//
//  AppDelegate.m
//  AccuroFit
//
//  Created by Yongfeng Li on 8/6/15.
//  Copyright (c) 2015 Nci Technology Inc. All rights reserved.
//
#import <CoreTelephony/CTCallCenter.h>
#import <CoreTelephony/CTCall.h>

#import <AudioToolbox/AudioServices.h>
#include <arpa/inet.h>
#import <SystemConfiguration/CaptiveNetwork.h>
#import "Reachability.h"

#import "ViewController.h"
#import "UIUserRegViewController.h"
#import "UILoginViewController.h"
#import "AppDelegate.h"

#import "HeaRateViewCtrl.h"

//DbObj
#import "N_DataGoals.h"
#import "N_WgtData.h"
#import "N_FatData.h"
#import "H_Rate.h"
#import "H_RateRng.h"
#import "H_RateItem.h"
#import "N_BdpData.h"
#import "P_Steps.h"
#import "N_GroupInfo.h"

#import "O-Hrate.h"
#import "O-HrateItem.h"

//#include <TargetConditionals.h>

#define kReg_BodyId @"Reg_BodyId"
#define kReg_TagId @"Reg_TagId"

#define kReg_BornDate @"Reg_BornDate"
//#define kReg_BodyAge @"Reg_BodyAge", dynamic change, not solid const
#define kReg_Gender @"Reg_Gender"
#define kReg_BodyWgt @"kReg_BodyWgt"
#define kReg_WgtGoal @"kReg_WgtGoal"
#define kReg_WgtUnit @"Reg_WgtUnit"
#define kReg_BodyHgt @"Reg_BodyHgt"
#define kReg_HgtUnit @"Reg_HgtUnit"
#define kReg_ActLevel @"Reg_ActLevel"

#define kReg_BodyEmail @"Reg_BodyEmail"
#define kReg_FirstName @"Reg_FirstName"
#define kReg_LastName @"Reg_LastName"
#define kReg_BodyHgtMm @"Reg_BodyHgtMm"

#define kReg_BodyChest @"Reg_BodyChest"
#define kReg_BodyWaist @"Reg_BodyWaist"

#define kReg_GoalStep @"Reg_GoalStep"
#define kReg_GoalDistan @"Reg_GoalDistan"
#define kReg_GoalDistUn @"Reg_GoalDistUn"

#define kReg_MaxBpm @"Reg_MaxBpm"

#define kReg_UserMgr @"Reg_UserMgr"
#define kReg_ClubAdmin @"Reg_ClubAdmin"


#define kNext_GoalId @"Next_GoalId"
#define kNext_WgtId @"Next_WgtId"

#define kCount_HRate @"Count_Hrate"
#define kNext_HrateId @"Next_HrateId"
#define kNext_HrmMeasId @"Next_HmeasId"
#define kNext_HrmItemId @"Next_HitemId"

#define _ScaleHostPort 3000
#define _ScaleHostIpAddr "193.169.1.1"

static BOOL _bChinese = NO;
static BOOL _bIniCoreData = NO;
static NSMutableArray* _maLastData = nil;

static NSDate* _dtHrtStart = nil;

static BOOL _bCellCallConn = NO;
static BOOL _b4GNetConn = NO;
//chicago office debug dev
//static char _IP_ADDR_US[32] = "192.168.1.118";
//static char _IP_ADDR_CN[32] = "192.168.1.118";

//Nanjing home local
//static char _IP_ADDR_US[32] = "192.168.1.121";
//static char _IP_ADDR_CN[32] = "192.168.1.121";

//Chicago Office IP svr
//static char _IP_ADDR_US[32] = "172.125.33.231";
//static char _IP_ADDR_CN[32] = "172.125.33.231";

//Chicago Office IP test
//static char _IP_ADDR_US[32] = "172.125.33.231";
//static char _IP_ADDR_CN[32] = "172.125.33.231";

//Nanjing
//static char _IP_ADDR_US[32] = "221.226.30.35";
//static char _IP_ADDR_CN[32] = "221.226.30.35";

//static char _IP_ADDR_US[32] = "192.168.0.100";
//static char _IP_ADDR_CN[32] = "192.168.0.100";

//test
//static char _IP_ADDR_US[32] = "221.226.30.35";
//static char _IP_ADDR_CN[32] = "221.226.30.35";
//static char _IP_ADDR_US[32] = "172.125.33.232";
//static char _IP_ADDR_CN[32] = "172.125.33.232";

static char _IP_ADDR_US[32] = "www.accurofitapp.net";
static char _IP_ADDR_CN[32] = "www.accurofitapp.net";

//customer
//static char _IP_ADDR_US[32] = "172.125.33.231";
//static char _IP_ADDR_CN[32] = "221.226.30.35";

@interface AppDelegate ()

@end

@implementation AppDelegate {
  id _goalDelegate;
  
  NSInteger _nLstHrtIdx;
  NSInteger _nLastHrtId;
  short _nLastHrate;
  short _nCurtAvgHrt;
  
  NSInteger _nLoginBodyId;
  NSString* _sLoginEmail;
  
  LoginBodyInfo* _bodyInfo;
  NSCalendar* _calendar;
    
  UINavigationController* _navController;
  ViewController* _viewController;
  UIViewController * _vcCurrent;
    
  //wifi
  BOOL _bCellConn;
  NSString* _ConnSsid;
    
  in_addr_t _nIpHost;
  BOOL _bHostConn;
  Reachability* _hostReach;
  NcitWiFiDev * _ncitWiFiDev;
    
  BOOL _bSupportBle;
  NcitBleDevice* _ncitBleDev;
    
  NSDateFormatter* _dtFmt;
    
  NSString* _dbName;
  NSString* _dbPath;
  BOOL _bDeleteCoreData;
    
  float _fStepLength;
    
  NSManagedObjectContext* _managedObjectContext;
  NSManagedObjectModel* _managedObjectModel;
  NSPersistentStoreCoordinator* _persistentStoreCoordinator;
  
  NSFetchRequest *_request;
  NSMutableArray* _maCoreData;
  
  BOOL _bStoredBleUuid;
  
  //hrm
  //HeaRateViewCtrl* _pHrmCtrl;
  H_Rate* _pHrate;
  NSInteger _nHrateId;
  
  //sync
  NSURLSession* _netSession;
  BOOL _bNetSessionEror;
  
  NSInteger _nLastBodyId;
  NSString* _sLastBodyName;
  
  CTCallCenter* _callCenter;
  
  //hrate meme
  NSInteger _nMemHrateId;
  NSMutableArray* _aHrateMemData;
  NSMutableArray* _aHrateItemMemData;
  BOOL _bJustSotreHrateMem;
}
@synthesize m_pRootViewCtrl = _viewController;

@synthesize m_nLoginBodyId = _nLoginBodyId;
@synthesize m_sLoginEmail = _sLoginEmail;
@synthesize m_bodyInfo = _bodyInfo;
@synthesize m_calendar = _calendar;
@synthesize m_bHostConn = _bHostConn;
@synthesize m_ncitWiFiDev = _ncitWiFiDev;

@synthesize m_bSupportBle = _bSupportBle;
@synthesize m_ncitBleDev = _ncitBleDev;
@synthesize m_pNavController = _navController;

@synthesize  m_fStepLength = _fStepLength;
@synthesize m_bStoredBleUuid = _bStoredBleUuid;
@synthesize dtFmt = _dtFmt;

@synthesize m_pHrate = _pHrate;
@synthesize m_nHrateId = _nHrateId;

@synthesize m_bClearCoreData = _bDeleteCoreData;

@synthesize m_nLstHrtIdx = _nLstHrtIdx;
@synthesize m_nLastHrtId = _nLastHrtId;
@synthesize m_nLastHrate = _nLastHrate;
@synthesize m_nCurtAvgHrt = _nCurtAvgHrt;

@synthesize m_nLastBodyId = _nLastBodyId;
@synthesize m_sLastBodyName = _sLastBodyName;

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
  _nLoginBodyId = 0;
  _dtFmt = nil;
  _bodyInfo = nil;
  
  _nLastHrtId = -1;
  _nLastHrate = 0;
  _nCurtAvgHrt = 0;
  
  _bIniCoreData = NO;
  _fStepLength = 0.0f;
  _maCoreData = nil;
  
  _bDeleteCoreData = NO;
  
  //hrm
  _pHrate = nil;
  _nHrateId = 0;
  _bNetSessionEror = NO;
  _bStoredBleUuid = NO;
  
  _bChinese = [[AppDelegate currentLanguage] hasPrefix:@"zh-Hans"];
  
  _calendar = [[NSLocale currentLocale] objectForKey:NSLocaleCalendar];//[[NSCalendar currentCalendar] objectForKey:NSLocaleCalendar];
  //[_calendar setLocale:    //wait 0.5 s for launch page
  //[NSThread sleepForTimeInterval:0.5];
  
  [self getRegInfoInUserDefaults];
  [self initWiFiBLEDev];
  [[UIApplication sharedApplication] setStatusBarOrientation:UIInterfaceOrientationPortrait];
    
    // Override point for customization after application launch.
  self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
  _viewController = [[ViewController alloc] init];
    
  _navController = [[UINavigationController alloc] init];
  _navController.navigationBar.barStyle = UIBarStyleBlackTranslucent;//UIBarStyleBlack;
  //_navController.navigationBar.backgroundColor = [UIColor grayColor];
  
  /*CGFloat fTitWid = 228;
  UIImage* iNav = [UIImage imageNamed:@"ic-accuro-n.png"];
  //UIImage* iNav = [self getImageScale:@"ic-accuro-n.png" scale:0.5];
  CGRect rt = _navController.navigationBar.frame;
  
  //CGFloat fScale = [UIScreen mainScreen].scale;
  CGFloat fHgtDelta = 0;//(fScale >= 3.0)? 2: 0;
  UIImageView *ivNav = [[UIImageView alloc] initWithFrame:CGRectMake((rt.size.width-fTitWid)/2 + 0, 0, fTitWid, 30 - fHgtDelta)];
  [ivNav setImage:iNav];
  // setContent mode aspect fit
  [ivNav setContentMode:UIViewContentModeScaleAspectFit];*/
  //[[UINavigationBar appearance] setBackgroundImage:[UIImage imageNamed:@"ic-accuro-n.png"] forBarMetrics:UIBarMetricsDefault];
   //ivNav.alpha = 0.5;
  /*if(fScale >= 3.0) {
    rt.size.height -= 4;
    _navController.navigationBar.frame = rt;
  }*/
  //[_navController.navigationBar addSubview:ivNav];
    
  BOOL bReged = [self isBodyLogged];
  if(bReged) {
    [self showLogingInToolBar];
    [_navController pushViewController:_viewController animated:YES];
    /*UIStoryboard* mainStory = [UIStoryboard storyboardWithName:@"Main" bundle:nil];
    UIUserRegViewController * vcReg = [mainStory instantiateViewControllerWithIdentifier:@"mianViewCtrl"];
    [_navController pushViewController:vcReg animated:YES];*/
  }
  else {
    UIStoryboard* mainStory = [UIStoryboard storyboardWithName:@"Main" bundle:nil];
    UIUserRegViewController * vcReg = [mainStory instantiateViewControllerWithIdentifier:@"userRegWaitVC"];
    [_navController pushViewController:vcReg animated:YES];
  }
  self.window.rootViewController = _navController;
  [self.window makeKeyAndVisible];
    
  [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent];
  
  if(!_bIniCoreData) {
    if(![self initCoreData]) {
      [self initCoreData];
    }
  }
  
  NSSetUncaughtExceptionHandler(&uncaughtExceptionHandler);
  
  //sync session
  NSURLSessionConfiguration* cnfgSession = [NSURLSessionConfiguration defaultSessionConfiguration];// [NSURLSessionConfiguration backgroundSessionConfigurationWithIdentifier: @"HrateSync"];
  cnfgSession.timeoutIntervalForRequest = 10.0; 
  _netSession = [NSURLSession sessionWithConfiguration:cnfgSession delegate: self delegateQueue: nil];
  //[self setHrateRcdCount]; don't call avoid user delete rcd
  
  _nLastBodyId = 0;
  _sLastBodyName = nil;
  
  //test
  /*NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  NSInteger nNext_Store = [userSetting integerForKey:kCount_HRate];
  NSInteger nNext_HrateId = [self getHrateRcdCount];
  int n = (int)nNext_HrateId;*/
  
  //_viewController.presentsWithGesture = NO;
  
  self.m_bDownloadHrmMemory = YES;
  _vcCurrent = nil;
  
  _callCenter = [[CTCallCenter alloc] init];
  [self setPhoneCallNotication];
  
  _aHrateMemData = nil;
  _aHrateItemMemData = nil;
  _nMemHrateId = 0;
  
  _bJustSotreHrateMem = NO;
  
  return YES;
}

- (void) storeHrateMemData
{
  if(_aHrateMemData == nil || _aHrateMemData.count == 0 || _aHrateItemMemData == nil || _aHrateItemMemData.count == 0)
    return;
 
  _bJustSotreHrateMem = YES;
  NSInteger nCount = _aHrateMemData.count;
  AppDelegate *pApp = (AppDelegate *)[[UIApplication sharedApplication] delegate];
  
  //O_Hrate* objLast = [_aHrateMemData objectAtIndex:nCount-1];
  
  for(NSInteger i=0; i<nCount; i++) {
    O_Hrate* objHrate = [_aHrateMemData objectAtIndex:i];
    NSUInteger utcFirst = objHrate.nSyncMeasStartUtc;
    NSUInteger utcEnd = objHrate.nSyncMeasEndUtc;
    NSDate* dtFirst = [NSDate dateWithTimeIntervalSince1970:(NSTimeInterval)utcFirst];
    NSDate* dtEnd = [NSDate dateWithTimeIntervalSince1970:(NSTimeInterval)utcEnd];
    
    H_Rate* _pRate = [self insertHrateData:NO bodyId:_bodyInfo.m_nBodyId hrateId:&_nMemHrateId time:dtFirst toSvr:NO];
    if(_nMemHrateId != 0 && _pRate != nil) {
      [self updHrateStartEndTime:_pRate startTime:nil endTime:dtEnd toSvr:NO];
    }
    else if(_nMemHrateId == 0) {
      [pApp showAlertBox:NSLocalizedString(@"save data to DB", nil) msg:NSLocalizedString(@" insert data to databse error happened!", nil)];
      continue;
    }
    
    
    int nHrateId = objHrate.nHrateId;
    NSUInteger nItemCount = _aHrateItemMemData.count;
    for(NSUInteger j=0; j<nItemCount; j++) {
      O_HrateItem* item = [_aHrateItemMemData objectAtIndex:j];
      if(item == nil || item.nHrateId != nHrateId)
        continue;
      
      short nBpm = item.nHrateVal;
      NSUInteger nMeasUtc = item.nSyncMeasUtc;
      NSDate* dtItem = [NSDate dateWithTimeIntervalSince1970:(NSTimeInterval)nMeasUtc];
      
      //dispatch_async(dispatch_get_main_queue(), ^{
      [pApp insertHrateItemData:_nMemHrateId bodyId:_bodyInfo.m_nBodyId hRate:nBpm dtime: dtItem toSvr: NO];
      //});
      
      //NSString* sMsg = [NSString stringWithFormat:@"Store Memory Data (%ld/%ld)", (unsigned long)(j+1), (unsigned long)nItemCount];
      //[self performSelectorInBackground:@selector(showSyncMessage:) withObject:sMsg];
    }
  }
  
  [_aHrateMemData removeAllObjects];
  [_aHrateItemMemData removeAllObjects];
  //_bJustSotreHrateMem = NO;
}

- (void)applicationWillResignActive:(UIApplication *)application {
    // Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state.
    // Use this method to pause ongoing tasks, disable timers, and throttle down OpenGL ES frame rates. Games should use this method to pause the game.
  if(_aHrateMemData == nil && _aHrateItemMemData == nil && _vcCurrent != nil && [_vcCurrent isKindOfClass:[HeaRateViewCtrl class]]) {
    _aHrateMemData = ((HeaRateViewCtrl*)_vcCurrent).m_aHrateMemData;
    _aHrateItemMemData = ((HeaRateViewCtrl*)_vcCurrent).m_aHrateItemMemData;
  }
}

- (void)applicationDidEnterBackground:(UIApplication *)application {
  // Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later.
  // If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits.
  if(_bJustSotreHrateMem)
    return;
  
  if(_aHrateMemData == nil && _aHrateItemMemData == nil && _vcCurrent != nil && [_vcCurrent isKindOfClass:[HeaRateViewCtrl class]]) {
    _aHrateMemData = ((HeaRateViewCtrl*)_vcCurrent).m_aHrateMemData;
    _aHrateItemMemData = ((HeaRateViewCtrl*)_vcCurrent).m_aHrateItemMemData;
  }
  
  if(_aHrateMemData != nil && _aHrateItemMemData != nil) {
    if(_aHrateMemData.count == 0 || _aHrateItemMemData.count == 0)
      return;
    
    [self storeHrateMemData];
  }
}

- (void)applicationWillEnterForeground:(UIApplication *)application {
  // Called as part of the transition from the background to the inactive state; here you can undo many of the changes made on entering the background.
  if(_aHrateMemData != nil && _aHrateItemMemData != nil) {
    //[_navController pushViewController:_viewController animated:YES];
    [_viewController setMsgTitle:NSLocalizedString(@"Busy for store last data", nil)];
  }
  
  if(_bJustSotreHrateMem)
    return;
  
  if(_aHrateMemData != nil && _aHrateItemMemData != nil) {
    if(_aHrateMemData.count == 0 || _aHrateItemMemData.count == 0)
      return;
    
    //((HeaRateViewCtrl*)_vcCurrent).m_aHrateMemData = _aHrateMemData;
    //((HeaRateViewCtrl*)_vcCurrent).m_aHrateItemMemData = _aHrateItemMemData;
    [self storeHrateMemData];
  }
}

- (void)applicationDidBecomeActive:(UIApplication *)application {
    // Restart any tasks that we`re paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface.
  if(_bJustSotreHrateMem)
    return;
  
  if(_aHrateMemData != nil && _aHrateItemMemData != nil) {
    if(_aHrateMemData.count == 0 || _aHrateItemMemData.count == 0)
      return;
    
    [self storeHrateMemData];
  }
  
  _bJustSotreHrateMem = NO;
}

- (void)applicationWillTerminate:(UIApplication *)application {
    // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:.
    // Saves changes in the application's managed object context before the application terminates.
  if(_pHrate != nil && _nHrateId > 0) {
    [self updHrateStartEndTime:_pHrate startTime:nil endTime:[NSDate date] toSvr:YES];
  }
  [self saveContext];
}

-(void)application:(UIApplication *)application handleEventsForBackgroundURLSession:(NSString *)identifier completionHandler:(void (^)())completionHandler
{
  if ([identifier isEqualToString:[NSString stringWithUTF8String:(const char *)_IP_ADDR_US]])  {
    NSLog(@"background handle");
  }
}

- (UIInterfaceOrientationMask)application:(UIApplication *)application supportedInterfaceOrientationsForWindow:(UIWindow *)window {
    return UIInterfaceOrientationMaskPortrait;//UIInterfaceOrientationMaskAll;
}

+ (NSString*) currentLanguage
{
    NSString * currentLanguage = [[NSLocale preferredLanguages] objectAtIndex:0];
    return currentLanguage;
}

+ (BOOL) isLanguageChines
{
    return _bChinese;//[[eWgtAppDelegate currentLanguage] hasPrefix:@"zh-Hans"];
}

#pragma mark - BLE device
- (void) initWiFiBLEDev
{
    //wifi init
    _bCellConn = NO;
    _ConnSsid = @"";
    _nIpHost = 0;
    _bHostConn = NO;
    _hostReach = nil;
    _ncitWiFiDev = [[NcitWiFiDev alloc] init];
    
    //ble
    _bSupportBle = YES;
    _ncitBleDev = [[NcitBleDevice alloc] initBleDevice];
    _ncitBleDev.bleDelegate = self;
}

- (void) bleSupport:(BOOL)bSupport
{
  _bSupportBle = bSupport;
  
  //#if TARGET_OS_SIMULATOR
  NSProcessInfo *processInfo = [NSProcessInfo processInfo];
  if (processInfo.environment[@"SIMULATOR_DEVICE_NAME"] != nil) {
    _bSupportBle = YES;
  }
  
  //device is simulator
  _ncitBleDev.bleDelegate = nil;
}


#pragma mark - Web Api
- (NSMutableURLRequest*) requestWebApiRouter:(NSString*)sHttpMethod url:(NSString*)sUrl data:(NSDictionary*)dicData
{
  char* pIpAddr = [self getRemoteSvrIp];
  
  //NSCharacterSet *set = [NSCharacterSet URLHostAllowedCharacterSet];
  //sUrl= [sUrl stringByAddingPercentEncodingWithAllowedCharacters:set];
   sUrl = [sUrl stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];
  
  // 1.URL
  NSURL *url = nil;//[NSURL URLWithString:[NSString stringWithFormat:@"http://%s/AccuroFitSvr/api/%@", pIpAddr, sUrl]];
  if(strstr(pIpAddr, "30.35"))
    url = [NSURL URLWithString:[NSString stringWithFormat:@"http://%s:81/AccuroFitSvr/api/%@", pIpAddr, sUrl]];
  else
    url = [NSURL URLWithString:[NSString stringWithFormat:@"http://%s/AccuroFitSvr/api/%@", pIpAddr, sUrl]];
  //NSURL *url = [NSURL URLWithString:@"http://localhost:8080/MJServer/order"];
  if(url == nil)
    return nil;
    
  /*if([sHttpMethod hasPrefix:@"PUT"]) {
     GTSessionManager * manager = [GTSessionManager manager]; 
    
  }
  else {*/
    // 2.请求
    NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url];
    
    // 3.请求方法
    request.HTTPMethod = sHttpMethod;
  //}
    
    // 4.设置请求体（请求参数）, 创建一个描述订单信息的JSON数据
  if(dicData != nil) {
    NSData *json = [NSJSONSerialization dataWithJSONObject:dicData options:NSJSONWritingPrettyPrinted error:nil];
    request.HTTPBody = json;

    // 5.设置请求头：这次请求体的数据不再是普通的参数，而是一个JSON数据
    [request setValue:@"application/json" forHTTPHeaderField:@"Content-Type"];
  }
  
  /*if([sHttpMethod hasPrefix:@"PUT"]) {
    [request setValue:@"application/json" forHTTPHeaderField:@"Accept"];
    [request setValue:@"application/x-www-form-urlencoded" forHTTPHeaderField:@"Content-Type"];
  }*/
    
  return request;
}

- (void) setUserLoginInfo:(NSArray*)jsonArray email:(NSString*)sEmail
{
  if(_bodyInfo == nil) {
    _bodyInfo = [[LoginBodyInfo alloc] init];
  }
  _bodyInfo.sEmail = sEmail;
  
  [self setUserBodyProfile:jsonArray bodyInfo:_bodyInfo];
  
  for(NSDictionary *item in jsonArray) {
     NSString* sUnitType = [item objectForKey:@"_nType"];
    int nUnitType = sUnitType.intValue;
    
    if(nUnitType < 11) {
      NSString* sBodyId = [item objectForKey:@"_nBodyId"];
      _bodyInfo.m_nBodyId = sBodyId.integerValue;
      _nLoginBodyId = _bodyInfo.m_nBodyId;
      _sLoginEmail = _bodyInfo.sEmail;
    }
  }
  
  /*NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  [userSetting setInteger:_bodyInfo.m_nBodyId forKey:kReg_BodyId];
  [userSetting setObject:_bodyInfo.m_sTagId forKey:kReg_TagId];
  
  [userSetting setObject:_bodyInfo.sEmail forKey:kReg_BodyEmail];
  [userSetting setObject:_bodyInfo.sFirst forKey:kReg_FirstName];
  [userSetting setObject:_bodyInfo.sLast forKey:kReg_LastName];
  
  [userSetting setFloat:_bodyInfo.fBodyWgt forKey:kReg_BodyWgt];
  [userSetting setInteger:_bodyInfo.nWgtUn forKey:kReg_WgtUnit];*/
  [self storeRegInfoInUserDefaults];
}

- (void) saveRegBodyInfo:(NSInteger)nBodyId  email:(NSString*)sEmail first:(NSString*)sFirst last:(NSString*)sLast tagId:(NSString*)sTagId
{
  if(_bodyInfo == nil) {
    _bodyInfo = [[LoginBodyInfo alloc] init];
  }
  _bodyInfo.m_nBodyId = nBodyId;
  _bodyInfo.m_sUserId = @"0";
  _bodyInfo.m_sTagId = sTagId;
  
  _bodyInfo.sEmail = sEmail;
  _bodyInfo.sFirst = sFirst;
  _bodyInfo.sLast = sLast;
  
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  [userSetting setInteger:_bodyInfo.m_nBodyId forKey:kReg_BodyId];
  [userSetting setObject:_bodyInfo.m_sTagId forKey:kReg_TagId];
  
  [userSetting setObject:_bodyInfo.sEmail forKey:kReg_BodyEmail];
  [userSetting setObject:_bodyInfo.sFirst forKey:kReg_FirstName];
  [userSetting setObject:_bodyInfo.sLast forKey:kReg_LastName];
  
  _nLoginBodyId = _bodyInfo.m_nBodyId;
}

- (void) storeRegBodyInfo:(NSInteger)nBodyId tag:(NSString*)sTagId gerder:(Byte)nGender born:(NSDate*)dtBorn wgt:(float)fWgt wun:(Byte)nWu
                      hgt:(float)fHgt hun:(Byte)nHu lvl:(Byte)nActLvl email:(NSString*)sEmail first:(NSString*)sFirst last:(NSString*)sLast
                    store:(NSString*)sStore
{
  //for Sql not work
  if(nBodyId <= 0) {
    nBodyId = 1;
    nGender = 1;
    dtBorn = [[NSDate date] dateByAddingTimeInterval:(-86400*365*30)];
    fWgt = 132;
    nWu = 2;
    fHgt = 5.6;
    nHu = 2;
    sEmail = @"ylee@no-sql.com";
    sFirst = @"Test";
    sLast = @"NoSql";
  }
  
  if(_bodyInfo == nil) {
    _bodyInfo = [[LoginBodyInfo alloc] init];
  }
  _bodyInfo.m_nBodyId = nBodyId;
  _bodyInfo.m_sTagId = sTagId;
    
  _bodyInfo.dtBorn = dtBorn;
  _bodyInfo.nGender = nGender;
  _bodyInfo.fBodyWgt = fWgt;
  _bodyInfo.nWgtUn = nWu;
  _bodyInfo.fBodyHgt = fHgt;
  _bodyInfo.nHgtUn = nHu;
  _bodyInfo.nActLvl = nActLvl;
    
  if(sEmail != nil)
    _bodyInfo.sEmail = sEmail;
  if(sFirst != nil) {
    _bodyInfo.sFirst = sFirst;
    _bodyInfo.sLast = sLast;
  }
    
  float fHgtMm = fHgt;
  if(nHu == 2) {
    fHgtMm = fHgt * _FtToMeter;
  }
  _bodyInfo.nHgtMm = (short)(fHgtMm * 1000);
    
  if(dtBorn != nil) {
    [self setBodyYearAge:dtBorn];
  }
  else {
    _bodyInfo.nYearAge = 0;
  }
  _bodyInfo.sStoreLoc = sStore;
    
  [self storeRegInfoInUserDefaults];
}

- (void) setBodyYearAge:(NSDate*) dtBorn
{
  NSDateComponents *dtYear = [[NSCalendar currentCalendar] components:NSCalendarUnitYear fromDate:[NSDate date]];
  NSDateComponents *dtComp = [[NSCalendar currentCalendar] components:NSCalendarUnitYear fromDate:dtBorn];
  _bodyInfo.nYearAge = dtYear.year - dtComp.year - 1;
  dtYear = [[NSCalendar currentCalendar] components:NSCalendarUnitMonth fromDate:[NSDate date]];
  dtComp = [[NSCalendar currentCalendar] components:NSCalendarUnitMonth fromDate:dtBorn];
  //NSInteger m1= dtComp.month;
  //NSInteger m2 = dtYear.month;
  if(dtYear.month > dtComp.month) {
    _bodyInfo.nYearAge += 1;
  }
  else if(dtYear.month == dtComp.month) {
    dtYear = [[NSCalendar currentCalendar] components:NSCalendarUnitDay fromDate:[NSDate date]];
    dtComp = [[NSCalendar currentCalendar] components:NSCalendarUnitDay fromDate:dtBorn];
    //NSInteger d1 = dtComp.day;
    //NSInteger d2 = dtYear.day;
    if(dtYear.day >= dtComp.day)
      _bodyInfo.nYearAge += 1;
  }
 
  [self setDefaultnMaxBpm];
}

- (void) storeRegInfoInUserDefaults
{
  if(_bodyInfo == nil) {
    _bodyInfo = [[LoginBodyInfo alloc] init];
  }
  
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  if(_nLoginBodyId > 0)
    [userSetting setInteger:_nLoginBodyId forKey:kReg_BodyId];
  [userSetting setObject:_bodyInfo.m_sTagId forKey:kReg_TagId];
    
  [userSetting setObject:[_bodyInfo getBornDate] forKey:kReg_BornDate];
  [userSetting setInteger:_bodyInfo.nGender forKey:kReg_Gender];
    
    
  //[userSetting setInteger:_bodyInfo.nYearAge forKey:kReg_BodyAge];
  [userSetting setFloat:_bodyInfo.fBodyWgt forKey:kReg_BodyWgt];
  [userSetting setFloat:_bodyInfo.fGoalWgt forKey:kReg_WgtGoal];
  [userSetting setInteger:_bodyInfo.nWgtUn forKey:kReg_WgtUnit];
  [userSetting setFloat:_bodyInfo.fBodyHgt forKey:kReg_BodyHgt];
  [userSetting setInteger:_bodyInfo.nHgtUn forKey:kReg_HgtUnit];
  [userSetting setInteger:_bodyInfo.nActLvl forKey:kReg_ActLevel];
  
  [userSetting setObject:_bodyInfo.sEmail forKey:kReg_BodyEmail];
  [userSetting setObject:_bodyInfo.sFirst forKey:kReg_FirstName];
  [userSetting setObject:_bodyInfo.sLast forKey:kReg_LastName];
  
  [userSetting setInteger:_bodyInfo.nHgtMm forKey:kReg_BodyHgtMm];
  [userSetting setObject:[NSString stringWithFormat:@"%0.1f", _bodyInfo.fChestSize] forKey:kReg_BodyChest];
  [userSetting setObject:[NSString stringWithFormat:@"%0.1f", _bodyInfo.fWaistLine] forKey:kReg_BodyWaist];
  
  
  [userSetting setInteger:_bodyInfo.nGoalStep forKey:kReg_GoalStep];
  [userSetting setFloat:_bodyInfo.fGoalDist forKey:kReg_GoalDistan];
  [userSetting setInteger:_bodyInfo.nDistUnit forKey:kReg_GoalDistUn];
  
  if(_bodyInfo.nMaxBpm > 0)
    [userSetting setInteger:_bodyInfo.nMaxBpm forKey:kReg_MaxBpm];
  
  [self setUserMgr:_bodyInfo.m_bMgr?1:0 admin:_bodyInfo.m_nClubAdmin];
    
  [userSetting synchronize];

  //update user info diaplay
  NSString* sName = @"";
    if(_bodyInfo.sFirst != nil){
        if ([self isChinese:_bodyInfo.sFirst]) {
            sName = [NSString stringWithString:_bodyInfo.sLast];
        } else {
            sName = [NSString stringWithString:_bodyInfo.sFirst];
        }
    }
    if(_bodyInfo.sLast != nil){
        //    sName = [sName stringByAppendingFormat:@" %@",_bodyInfo.sLast];
        if ([self isChinese:_bodyInfo.sLast]) {
            sName = [NSString stringWithFormat:@"%@ %@",sName,_bodyInfo.sFirst];
        } else {
            sName = [sName stringByAppendingFormat:@" %@",_bodyInfo.sLast];
        }
    }
  if(_bodyInfo.nHgtUn == 2) {
    short nFeet = (short)_bodyInfo.fBodyHgt;
    short nInch = (_bodyInfo.fBodyHgt - nFeet) * 12;
    NSString* sHgt = [NSString stringWithFormat:@"%i ft  %i in", nFeet, nInch];
    [_viewController updateUserInfo:sName age:_bodyInfo.nYearAge hgt:sHgt];
  }
  else {
     NSString* sHgt = [NSString stringWithFormat:@"%.1f cm",  _bodyInfo.fBodyHgt * 100];
    [_viewController updateUserInfo:sName age:_bodyInfo.nYearAge hgt:sHgt];
  }
  
  [_viewController setMsgTitle: sName];
}

-(BOOL)isChinese:(NSString *)str {
    for(int i=0; i< [str length];i++)
    { int a = [str characterAtIndex:i];
        if( a > 0x4e00 && a < 0x9fff)
        { return YES;
        }
    } return NO;
}

//- (LoginBodyInfo*) getRegInfoInUserDefaults
- (void) getRegInfoInUserDefaults
{
  //if(_nLoginBodyId <= 0)
    //return;
  
  if(_bodyInfo == nil) {
    _bodyInfo = [[LoginBodyInfo alloc] init];
    //self.m_bodyInfo = _bodyInfo;
  }
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  Byte nSvrIpIdx = (Byte)[userSetting integerForKey:kReg_BodySvrIdx];
  _bodyInfo.nSvrIpIdx = nSvrIpIdx;
  
    //if([userSetting integerForKey:kReg_BodyId] == 0) {
  if([userSetting integerForKey:kReg_BodyId] <= 0) {
    _dtFmt = [[NSDateFormatter alloc]init];
    if([AppDelegate isLanguageChines])
      [_dtFmt setDateFormat:@"yyyy-MM-dd"];
    else
      [_dtFmt setDateFormat:@"MM/dd/yyyy"];
    return;
  }
  
  if(_dtFmt == nil)
    _dtFmt = _bodyInfo.dtFmt;
  
  //_bodyInfo = [userSetting objectForKey:kRegBodyInfo];
  //return _bodyInfo

  
  _bodyInfo.m_nBodyId = [userSetting integerForKey:kReg_BodyId];
  _nLoginBodyId = _bodyInfo.m_nBodyId;
  
  _bodyInfo.sEmail = [userSetting objectForKey:kReg_BodyEmail];
  _bodyInfo.sFirst = [userSetting objectForKey:kReg_FirstName];
  _bodyInfo.sLast = [userSetting objectForKey:kReg_LastName];
  _bodyInfo.m_sTagId = [userSetting objectForKey:kReg_TagId];
    
  _bodyInfo.dtBorn = [_dtFmt dateFromString:[userSetting objectForKey:kReg_BornDate]];

  _bodyInfo.nGender = [userSetting integerForKey:kReg_Gender];
  //_bodyInfo.nYearAge = [userSetting integerForKey:kReg_BodyAge];
  [self setBodyYearAge:_bodyInfo.dtBorn];
  _bodyInfo.fBodyWgt = [userSetting floatForKey:kReg_BodyWgt];
  _bodyInfo.fGoalWgt = [userSetting floatForKey:kReg_WgtGoal];
  _bodyInfo.nWgtUn = [userSetting integerForKey:kReg_WgtUnit];
    
  _bodyInfo.fBodyHgt = [userSetting floatForKey:kReg_BodyHgt];
  _bodyInfo.nHgtUn = [userSetting integerForKey:kReg_HgtUnit];
  _bodyInfo.nActLvl = [userSetting integerForKey:kReg_ActLevel];
    
    
  _bodyInfo.nHgtMm = [userSetting integerForKey: kReg_BodyHgtMm];
  _bodyInfo.fChestSize = ((NSString*)[userSetting objectForKey: kReg_BodyChest]).floatValue;
  _bodyInfo.fWaistLine = ((NSString*)[userSetting objectForKey: kReg_BodyWaist]).floatValue;
  
  _bodyInfo.nGoalStep = (int)[userSetting integerForKey:kReg_GoalStep];
  _bodyInfo.fGoalDist = [userSetting floatForKey:kReg_GoalDistan];
  _bodyInfo.nDistUnit = (Byte)[userSetting integerForKey:kReg_GoalDistUn];
  
  _bodyInfo.nMaxBpm = (int)[userSetting integerForKey:kReg_MaxBpm];
  //int nMaxBmp = _bodyInfo.nMaxBpm;
    
  [self setGoalVals];
  if(_nLoginBodyId <= 0)
    _nLoginBodyId = _bodyInfo.m_nBodyId;
  
  _sLoginEmail = _bodyInfo.sEmail;
}

- (void) setGoalVals
{
    _nLoginBodyId = _bodyInfo.m_nBodyId;
    //get store wgt goal
    N_DataGoals* pGoal  = [self loadGoalData:_nLoginBodyId from:nil to:nil unitType:11 last:YES];
    if(pGoal != nil)
      _bodyInfo.fGoalWgt = pGoal.dataValue.floatValue;
    //else if(_bodyInfo.fGoalWgt == 0.0)
      //_bodyInfo.fGoalWgt = 0.0;
    
    //goal distance
    pGoal  = [self loadGoalData:_nLoginBodyId from:nil to:nil unitType:12 last:YES];
    if(pGoal != nil)
      _bodyInfo.fGoalDist = pGoal.dataValue.floatValue;
    //else
      //_bodyInfo.fGoalDist = 0.0;
  _bodyInfo.nDistUnit = [AppDelegate isLanguageChines]? 1: 2;
    
    
    //goal step
    pGoal  = [self loadGoalData:_nLoginBodyId from:nil to:nil unitType:13 last:YES];
    if(pGoal != nil)
      _bodyInfo.nGoalStep = (int)pGoal.dataValue.floatValue;
    //else
      //_bodyInfo.nGoalStep = 0;
  
  //max heart rate
  pGoal  = [self loadGoalData:_nLoginBodyId from:nil to:nil unitType:14 last:YES];
  if(pGoal != nil && pGoal.dataValue.floatValue > 0) {
    _bodyInfo.nMaxBpm = (int)(pGoal.dataValue.floatValue + 0.4);
  }
  else if(_bodyInfo.nMaxBpm == 0) {
    _bodyInfo.nMaxBpm = [self calHrateFitnessRng: NO];
  }
  //short nMaxBpm = _bodyInfo.nMaxBpm;

    
  _fStepLength = _bodyInfo.nHgtMm * 0.0404;
  
  //store default setting
}

- (BOOL) isBodyLogged
{
    //NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  //NSInteger nBodyId = _nLoginBodyId;
  return _nLoginBodyId > 0;
}

- (void) resetBodyData
{
  _nLoginBodyId = 0;
  _bodyInfo.m_nBodyId = 0;
  _bodyInfo.m_sTagId = @"";
  _bodyInfo.m_sUserId = @"";
  
  _bodyInfo.sEmail = @"";
  _bodyInfo.sFirst = @"";
  _bodyInfo.sLast = @"";
  
  _bodyInfo.fBodyWgt = 0.0f;
  _bodyInfo.fBodyHgt = 0.0f;
  _bodyInfo.nHgtMm = 0;
  
  _bodyInfo.nGoalStep = 0;
  _bodyInfo.fGoalDist = 0.0f;
  _bodyInfo.nDistUnit = 0;
  
  _bodyInfo.fChestSize = 0.0f;
  _bodyInfo.fWaistLine = 0.0f;
  
  _bodyInfo.nMaxBpm = 0;
  _nLstHrtIdx = 0;
  
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  [userSetting setInteger:0 forKey:kSync_LastDldIdx];
  [userSetting setInteger:0 forKey:kSync_LastSyncIdx];
  [userSetting setInteger:0 forKey:kSync_LastMemDldIdx];
  [userSetting synchronize];  
}

- (void) clearRegData
{
  [self resetBodyData];
  
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  [userSetting removeObjectForKey:kReg_BodyId];
  [userSetting removeObjectForKey:kReg_TagId];
  
  [userSetting removeObjectForKey:kReg_FirstName];
  [userSetting removeObjectForKey:kReg_LastName];
  
  [userSetting removeObjectForKey:_kStoredHMUuid];
  [userSetting removeObjectForKey:_kStoredPEUuid];
  
  [userSetting removeObjectForKey:kReg_MaxBpm];
  [userSetting setInteger:0 forKey:kReg_MaxBpm];
  
  [userSetting setInteger:0 forKey:kNext_GoalId];
  [userSetting setInteger:0 forKey:kCount_HRate];
  [userSetting setInteger:0 forKey:kNext_HrateId];
  [userSetting setInteger:0 forKey:kNext_HrmMeasId];
  [userSetting setInteger:0 forKey:kNext_HrmItemId];
  
  [userSetting setInteger:0 forKey:kSync_LastDldIdx];
  
  [userSetting synchronize];
}

- (void) userLogout
{
 
  [self resetBodyData];
  [self clearRegData];
  if(_ncitBleDev.bConnBleDev)
    [_ncitBleDev stopMeas];
  
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  [userSetting removeObjectForKey:kReg_BodyId];
  [userSetting removeObjectForKey:kReg_TagId];
  
  [userSetting removeObjectForKey:kReg_FirstName];
  [userSetting removeObjectForKey:kReg_LastName];
  
  [userSetting removeObjectForKey:_kStoredHMUuid];
  [userSetting removeObjectForKey:_kStoredPEUuid];
  
  [userSetting removeObjectForKey:kReg_MaxBpm];
  [userSetting setInteger:0 forKey:kReg_MaxBpm];
  
  [userSetting setInteger:0 forKey:kNext_GoalId];
  [userSetting setInteger:0 forKey:kCount_HRate];
  [userSetting setInteger:0 forKey:kNext_HrateId];
  [userSetting setInteger:0 forKey:kNext_HrmMeasId];
  [userSetting setInteger:0 forKey:kNext_HrmItemId];
  
  [userSetting setInteger:0 forKey:kSync_LastDldIdx];
  
  [userSetting synchronize];
  
  if(_ncitBleDev) {
    _ncitBleDev.bleDelegate = nil;
    [_ncitBleDev resetCurtSelUuid];
  }
    
  //_bodyInfo = nil;
    
  NSArray* arrViewCtrls = [_navController viewControllers];
  for(UIViewController *tempVC in arrViewCtrls) {
      [tempVC removeFromParentViewController];
  }
    
  arrViewCtrls = _navController.navigationItem.leftBarButtonItems;
  for(UIViewController *tempVC in arrViewCtrls) {
    [tempVC removeFromParentViewController];
  }
    
  UIStoryboard* mainStory = [UIStoryboard storyboardWithName:@"Main" bundle:nil];
  UILoginViewController* vcLogin = [mainStory instantiateViewControllerWithIdentifier:@"loginViewCtrl"];
  vcLogin.bLoguot = YES;
    
  //AppDelegate *pApp = (AppDelegate *)[[UIApplication sharedApplication] delegate];
    
  [self deleteDataHandler:nil tip:NO];
  [self.m_pNavController popToRootViewControllerAnimated:NO];
  [self.m_pNavController pushViewController:vcLogin animated:YES];
}

//debug
- (void) clearStoreData
{
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  [userSetting setInteger:0 forKey:kNext_GoalId];
  [userSetting setInteger:0 forKey:kCount_HRate];
  [userSetting setInteger:0 forKey:kNext_HrateId];
  [userSetting setInteger:0 forKey:kNext_HrmMeasId];
  [userSetting setInteger:0 forKey:kNext_HrmItemId];
  
  [self deleteDataHandler:nil tip:NO];
  [self.m_pNavController popToRootViewControllerAnimated:NO];
  
  UIStoryboard* mainStory = [UIStoryboard storyboardWithName:@"Main" bundle:nil];
  UILoginViewController* vcHrate = [mainStory instantiateViewControllerWithIdentifier:@"hrdRcdViewCtrl"];
  [self.m_pNavController pushViewController:vcHrate animated:YES];
}

- (void) enterMainPage
{
  //[_navController popViewControllerAnimated:NO];
  //[_navController popToRootViewControllerAnimated:NO];
  NSArray* arrViewCtrls = [_navController viewControllers];
  for(UIViewController *tempVC in arrViewCtrls)
  {
    //if([tempVC isKindOfClass:[ViewController class]]) {
    [tempVC removeFromParentViewController];
    //}
  }
  
  _viewController.navigationItem.hidesBackButton = YES;
  [_navController pushViewController:_viewController animated:YES];
  //[_navController presentedViewController:_viewController animated:YES];
  [self setGoalVals];
  //_navController.navigationItem.backBarButtonItem.title = @"";
  //_navController.navigationItem.backBarButtonItem = nil;
  _navController.navigationItem.leftItemsSupplementBackButton = NO;
}

- (UIViewController*) enterPageWithRes:(NSString*) sResId
{
  //[_navController popViewControllerAnimated:NO];
    
  UIStoryboard* mainStory = [UIStoryboard storyboardWithName:@"Main" bundle:nil];
  UIViewController * vCtrl = [mainStory instantiateViewControllerWithIdentifier:sResId];
    
  [_navController pushViewController:vCtrl animated:YES];
  _vcCurrent = vCtrl;
  
  return vCtrl;
}

- (UIImage*) getImageScale:(NSString*) sImgName scale:(float)fRate
{
    UIImage* imgBkgd = [UIImage imageNamed:sImgName];
    UIGraphicsBeginImageContext(CGSizeMake(imgBkgd.size.width * fRate, imgBkgd.size.height * fRate));
    [imgBkgd drawInRect:CGRectMake(0, 0, imgBkgd.size.width * fRate, imgBkgd.size.height * fRate)];
    UIImage *scaledImage = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();
    
    BOOL bIos7 = [[[UIDevice currentDevice] systemVersion] floatValue] >= 7.0;
    if(bIos7) {
        scaledImage = [scaledImage imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal];
    }
    return scaledImage;
}

- (UIImage*) imageWithImage:(UIImage *)image scaledToSize:(CGSize)newSize {
  // In next line, pass 0.0 to use the current device's pixel scaling factor (and thus account for Retina resolution).
  // Pass 1.0 to force exact pixel size.
  UIGraphicsBeginImageContextWithOptions(newSize, NO, 0.0);
  [image drawInRect:CGRectMake(0, 0, newSize.width, newSize.height)];
  UIImage *newImage = UIGraphicsGetImageFromCurrentImageContext();    
  UIGraphicsEndImageContext();
  return newImage;
}

#pragma mark - WiFi device
- (NSString *)connedWifiSSID {
    //NSString *ssid = nil;
    _ConnSsid = @"CellPhone";
    NSString* deviceType = [UIDevice currentDevice].model;
    if (![deviceType isEqualToString:@"iPhone"])
        _ConnSsid = @"No WiFi";
    NSArray *ifs = (__bridge NSArray *)CNCopySupportedInterfaces();
    if(ifs == nil)
        return @"nil";
    for (NSString *ifnam in ifs) {
        NSDictionary *info = (__bridge_transfer id)CNCopyCurrentNetworkInfo((__bridge CFStringRef)ifnam);
        if(info == nil)
            continue;
        if (info[@"SSID"]) {
            //ssid = info[@"SSID"];
            _ConnSsid = [NSString stringWithString:info[@"SSID"]];
        }
        info = nil;
    }
    
    CFRelease((CFTypeRef) ifs);
    return _ConnSsid;
    //return ssid;
    //return @"DBS210-CES1245";
}

- (char*) getRemoteSvrIp
{
  char* pIpAddr = NULL;
  Byte nSvrIdx = _bodyInfo.nSvrIpIdx;
  if(nSvrIdx == 1)
    pIpAddr = _IP_ADDR_CN;
  else
    pIpAddr = _IP_ADDR_US;
  
  /*if([AppDelegate isLanguageChines])
      pIpAddr = _IP_ADDR_CN;
  else
      pIpAddr = _IP_ADDR_US;*/
  return pIpAddr;
}

- (void) resetBodyId:(NSInteger)nBodyId
{
  //_nLoginBodyId = nBodyId;
  _bodyInfo.m_nBodyId = nBodyId;
  self.m_bodyInfo.m_nBodyId = nBodyId;
  [self resetBodyInfo];
}

- (void) resetBodyInfo {
  //[self getUserGoalData:NO];
  if(_nLoginBodyId != _bodyInfo.m_nBodyId) {
     N_GroupInfo* pBody = [self loadMemberUserData:_bodyInfo.m_nBodyId];
    
    _bodyInfo.m_sTagId = pBody.cardNo;
    NSString* sEmail = pBody.bodyEmail;
    NSRange rng = [sEmail rangeOfString:@" "];
    if(rng.location != NSNotFound) {
      _bodyInfo.sFirst = [sEmail substringWithRange: NSMakeRange(0, rng.location)];
      _bodyInfo.sLast = [sEmail substringFromIndex:(rng.location+1)];
    }
    if(sEmail != nil) {
      _bodyInfo.sFirst = sEmail;
      _bodyInfo.sLast = @"";
    }
    else {
      _bodyInfo.sFirst = @"";
       _bodyInfo.sLast = @"";
    }
    _bodyInfo.nGender = pBody.bodySex.shortValue;
    if([sEmail rangeOfString:@"@"].location != NSNotFound)
      _bodyInfo.sEmail = pBody.bodyEmail;
    else
      _bodyInfo.sEmail = @"";
    
    _bodyInfo.fBodyWgt = pBody.bodyWgt.floatValue;
    _bodyInfo.nWgtUn = pBody.wgtUnit.shortValue;
    _bodyInfo.fBodyHgt = pBody.bodyHgt.floatValue;
    _bodyInfo.nHgtUn = pBody.hgtUnit.shortValue;
    _bodyInfo.nHgtMm = _bodyInfo.fBodyHgt * 1000 * ((_bodyInfo.nHgtUn==2)?_FtToMeter:1);
    
    _bodyInfo.fChestSize = pBody.fChest.floatValue;
    _bodyInfo.fWaistLine = pBody.fWaist.floatValue;
    _bodyInfo.nActLvl = pBody.athleteLvl.shortValue;
    
    //NSString* sDtFmt = _dtFmt.dateFormat;
    //[_dtFmt setDateFormat:@"MM/dd/yyyy"];
    _bodyInfo.dtBorn = pBody.bodyAge;
    [self setBodyYearAge:_bodyInfo.dtBorn];
    
    [self.m_pRootViewCtrl setMsgTitle:_bodyInfo.sEmail];
    //_bodyInfo.nMaxBpm
  }
  else {
    //_bodyInfo.sFirst = @"First";
    //_bodyInfo.sLast = @"Last";
    [self getUserGoalData:YES];
    //[self getRegInfoInUserDefaults];
    NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
    _bodyInfo.sFirst = [userSetting objectForKey:kReg_FirstName];
    _bodyInfo.sLast = [userSetting objectForKey:kReg_LastName];
    _sLastBodyName = [NSString stringWithFormat:@"%@ %@",  _bodyInfo.sFirst, _bodyInfo.sLast];
  }
  
  //test
  /*short nAge = _bodyInfo.nYearAge;;
  NSString* sMsg = [NSString stringWithFormat:@"w=%.1f %@, h=%.4f %@(%i), a=%d", _bodyInfo.fBodyWgt, ((_bodyInfo.nWgtUn==2)?@"kg":@"kg"),
                    _bodyInfo.fBodyHgt, ((_bodyInfo.nHgtUn==2)?@"f":@"m"), _bodyInfo.nHgtMm, _bodyInfo.nYearAge];
  int m = 1;*/
}

- (void) activeCellConnThread
{
    NSError *error;
    NSURLResponse *response;
    _bCellConn = YES;
    //NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:@"http://www.apple.com"]];
    //NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:@"http://www.google.com/txt"]];
    //NSMutableURLRequest *request = [bodyId <= 0NSMutableURLRequest requestWithURL:[NSURL URLWithString:@"http://www.bing.com"]]
    NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:@"http://www.baidu.com"]];
    [request setHTTPMethod:@"GET"];
    //NSData* reData = [NSURLConnection sendSynchronousRequest:request returningResponse:&response error:&error];
    //NSString* strData;
    [NSURLConnection sendSynchronousRequest:request returningResponse:&response error:&error];
}

- (void) hostConnChged:(Reachability*) hostReach {
    NetworkStatus netStatus = [hostReach currentReachabilityStatus];
    if(_bHostConn && (netStatus == NotReachable))
        return;
    
    //NSArray *ctrlers = tabBarController.viewControllers;
    //CommViewController* commCtrler = [ctrlers objectAtIndex:0];
    
    //if(netStatus == ReachableViaWWAN) {
    if(netStatus != NotReachable) {
        if(_bHostConn)
            [_ncitWiFiDev turnConnOff];
        
        if(netStatus == ReachableViaWWAN)
            [self activeCellConnThread];
        
        _nIpHost = _hostReach.m_nIpAddr;
        _ncitWiFiDev.m_nIpAddr = _nIpHost;
        _bHostConn = [_ncitWiFiDev startOn];
    }
    else {
        //if(m_bHostConn)
        //return;
        _bHostConn = NO;
        _nIpHost = 0;
        [_ncitWiFiDev turnConnOff];
    }
    /*if (commCtrler) {
     [commCtrler refreshHostConn:m_bHostConn socketHost:m_socketHost];
     if (m_bHostConn)
     [commCtrler sendDataToSvr:NULL];
     }*/
    
}

//Called by Reachability whenever status changes.
- (void) reachabilityChanged: (NSNotification* )note
{
    //if(m_bHostConn)
    //return;
    Reachability* curReach = [note object];
    NSParameterAssert([curReach isKindOfClass: [Reachability class]]);
    [self hostConnChged: curReach];
}

- (BOOL) hostSvrConn: (uint16_t)nPort IpAddr: (char*) szIpAddr {
    //[[NSNotificationCenter defaultCenter] addObserver: self selector: @selector(reachabilityChanged:) name: kHostNetChgedNotification object: nil];
    
    //host on
    struct sockaddr_in addr4;
    memset(&addr4, 0, sizeof(addr4));
    addr4.sin_len = sizeof(addr4);
    addr4.sin_family = AF_INET;
    addr4.sin_port = htons(nPort);
    addr4.sin_addr.s_addr = (__uint32_t)inet_addr(szIpAddr);
    
    _hostReach = [Reachability reachabilityWithAddress: &addr4 mark:NO connRef:NO];
    NetworkStatus netStatus = [_hostReach currentReachabilityStatus];
    if(netStatus == ReachableViaWWAN)
        [self activeCellConnThread];
    
    [_hostReach startNotifier];
    //[self hostConnChged: m_hostReach];
    
    //_hostWiFiReach = [Reachability reachabilityWithAddress: &addr4 mark:YES connRef:NO];
    //[m_hostWiFiReach startNotifier];
    
    [[NSNotificationCenter defaultCenter] addObserver: self selector: @selector(reachabilityChanged:) name: kHostNetChgedNotification object: _hostReach];
    //[[NSNotificationCenter defaultCenter] addObserver: self selector: @selector(reachabilityChanged:) name: kHostWiFiChgedNotification object: m_hostWiFiReach];
    
    return [_hostReach currentReachabilityStatus] != NotReachable;// || [m_hostWiFiReach currentReachabilityStatus] != NotReachable;
}

- (BOOL) isNcitDeviceConned
{
  NSString* sConnSsid = [self connedWifiSSID];
  BOOL bOK = [self isNcitDeviceWithSsid:sConnSsid];
  return bOK;
}

- (BOOL) isNcitDeviceWithSsid:(NSString*) sConnSsid
{
  BOOL bOK = [sConnSsid hasPrefix:@"DBS2"] || [sConnSsid hasPrefix:@"BFS2"] || [sConnSsid hasPrefix:@"DB2"] || [sConnSsid hasPrefix:@"RIS2"] || [sConnSsid hasPrefix:@"IS2"]
  || [sConnSsid hasPrefix:@"BFS200"] || [sConnSsid hasPrefix:@"BFS200"];
  return bOK;
}

- (Boolean) ConnScaleHost:(BOOL) bConn IpAddr:(char*) szIpAddr
{
    if(_ncitWiFiDev != nil && [_ncitWiFiDev isConnNetwork]) {
        _bHostConn = YES;
        return YES;
    }
    
    //if(!m_bHostConn) {
    //m_bHostConn = [self.socketHost startOn];
    //return m_bHostConn;
    //}
    
    uint16_t nPort = _ScaleHostPort;
    char* pIpAddr = szIpAddr;
    if (pIpAddr == NULL) {
        pIpAddr = [self getRemoteSvrIp];
        //pIpAddr = [self getAppSvrIpAddr];
    }
    [_ncitWiFiDev setTypeIdx:-9]; //for conn remote server
    BOOL bReach = [self hostSvrConn: nPort IpAddr: pIpAddr];
    if (bConn) {
        if(bReach && !_bHostConn) {
            [_ncitWiFiDev setAddrPort:inet_addr(pIpAddr) port:nPort];
            _bHostConn = [_ncitWiFiDev startOn];
        }
        return _bHostConn;
    }
    else {
        return bReach;
    }
    
}

- (BOOL) ConnWiFiScaleHost:(BOOL)bConn IpAddr: (char*) szIpAddr Port:(uint16_t)nPort
{
  if(_ncitWiFiDev != nil && [_ncitWiFiDev isConnNetwork]) {
    _bHostConn = YES;
    return YES;
  }
  
  uint16_t nScalePort = nPort;
  if(nScalePort == 0)
     nScalePort = _ScaleHostPort;
  char* pIpAddr = szIpAddr;
  if (pIpAddr == NULL) {
    pIpAddr = _ScaleHostIpAddr;
  }
  [_ncitWiFiDev setTypeIdx:-9]; //for conn remote server
  BOOL bReach = [self hostSvrConn: nPort IpAddr: pIpAddr];
  if (bConn) {
    if(bReach && !_bHostConn) {
      [_ncitWiFiDev setAddrPort:inet_addr(pIpAddr) port:nScalePort];
      //_socketHost.m_nIpAddr = inet_addr(_IP_ADDR);
      _bHostConn = [_ncitWiFiDev startOn];
    }
    return _bHostConn;
  }
  else {
    return bReach;
  }
}

- (void) resetHostConn
{
    _bHostConn = NO;
}

- (void)CloseScaleHost
{
    //if(m_bHostConn && self.socketHost) {
    if(_ncitWiFiDev != nil && [_ncitWiFiDev isConnNetwork]) {
        [_ncitWiFiDev turnConnOff];
    }
    _bHostConn = NO;
}


#pragma mark - Core Data stack

@synthesize managedObjectContext = _managedObjectContext;
@synthesize managedObjectModel = _managedObjectModel;
@synthesize persistentStoreCoordinator = _persistentStoreCoordinator;

//network connention state
- (BOOL) isNetWorkConnAvailable
{
  BOOL bOK = NO;
  _b4GNetConn = NO;
  
  char* szSvrIp = [self getRemoteSvrIp];
  NSString* sSvrIpAdd = [NSString stringWithUTF8String:szSvrIp];//[NSString stringWithFormat:@"%s", szSvrIp];
  Reachability* networkReach = [Reachability reachabilityWithHostName:sSvrIpAdd hostAddr:0];
  NetworkStatus netStatus = [networkReach currentReachabilityStatus];
  
  switch (netStatus) {
    case NotReachable: {
      bOK  = NO;
      break;
    }
      
    case ReachableViaWWAN: {
      _b4GNetConn = YES;
      bOK = YES;
      break;
    }
    case ReachableViaWiFi: {
      bOK = YES;
      break;
    }
  }
  
  return bOK;
}

- (BOOL) initCoreData {
  //return NO;
  
  _dbName = @"AccuroFit.sqlite";
  NSString* dAppDir = [self applicationDocumentsDirString];
  if(dAppDir)
    _dbPath = [dAppDir stringByAppendingPathComponent:_dbName];
    
    //[self removeAllCoreData];
  NSManagedObjectContext *context = [self managedObjectContext];
  if (!context) {
    // Handle the error.
    //[self removeAllCoreData];
     [context setMergePolicy:NSMergeByPropertyObjectTrumpMergePolicy];
  }
  _request = [[NSFetchRequest alloc] init];
  _bIniCoreData = YES;
  
    
  return context != nil;
}

- (NSString *) applicationDocumentsDirString {
    
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *basePath = ([paths count] > 0) ? [paths objectAtIndex:0] : nil;
    return basePath;
}

- (NSURL *) applicationDocumentsDirectory {
    // The directory the application uses to store the Core Data store file. This code uses a directory named "Nci-Technology-Inc..AccuroFit" in the application's documents directory.
    return [[[NSFileManager defaultManager] URLsForDirectory:NSDocumentDirectory inDomains:NSUserDomainMask] lastObject];
}

- (NSManagedObjectModel *)managedObjectModel {
    // The managed object model for the application. It is a fatal error for the application not to be able to find and load its model.
  if (_managedObjectModel != nil) {
    return _managedObjectModel;
  }
  NSURL *modelURL = [[NSBundle mainBundle] URLForResource:@"AccuroFit" withExtension:@"momd"];
  if(modelURL == nil)
    modelURL = [[NSBundle bundleForClass:[self class]] URLForResource:@"AccuroFit" withExtension:@"momd"];
  _managedObjectModel = [[NSManagedObjectModel alloc] initWithContentsOfURL:modelURL];
  return _managedObjectModel;
}

- (NSPersistentStoreCoordinator *)persistentStoreCoordinator {
    // The persistent store coordinator for the application. This implementation creates and return a coordinator, having added the store for the application to it.
    if (_persistentStoreCoordinator != nil) {
        return _persistentStoreCoordinator;
    }
    // Create the coordinator and store
    
  _persistentStoreCoordinator = [[NSPersistentStoreCoordinator alloc] initWithManagedObjectModel:[self managedObjectModel]];
  
  NSURL *storeURL = [[self applicationDocumentsDirectory] URLByAppendingPathComponent:@"AccuroFit.sqlite"];
  NSError *error = nil;
  //NSDictionary* dicOption = @{NSMigratePersistentStoresAutomaticallyOption:@YES, NSInferMappingModelAutomaticallyOption:@YES};
 
  
  //[_persistentStoreCoordinator addPersistentStoreWithType:NSSQLiteStoreType configuration:nil URL:storeURL options:dicOption error:&error];
  //return _persistentStoreCoordinator;
  NSDictionary *pragmaOptions = [NSDictionary dictionaryWithObject:@"MEMORY" forKey:@"journal_mode"];
  
  NSDictionary *dicOption = [NSDictionary dictionaryWithObjectsAndKeys:
                           [NSNumber numberWithBool:YES], NSMigratePersistentStoresAutomaticallyOption,
                           [NSNumber numberWithBool:YES], NSInferMappingModelAutomaticallyOption,
                           pragmaOptions, NSSQLitePragmasOption, nil];
 
   NSString *failureReason = @"There was an error creating or loading the application's saved data.";
  if (![_persistentStoreCoordinator addPersistentStoreWithType:NSSQLiteStoreType configuration:nil URL:storeURL options:dicOption error:&error]) { //replace nill with dicIption
    // Report any error we got.
    NSMutableDictionary *dict = [NSMutableDictionary dictionary];
    dict[NSLocalizedDescriptionKey] = @"Failed to initialize the application's saved data";
    dict[NSLocalizedFailureReasonErrorKey] = failureReason;
    dict[NSUnderlyingErrorKey] = error;
    error = [NSError errorWithDomain:@"YOUR_ERROR_DOMAIN" code:9999 userInfo:dict];
    // Replace this with code to handle the error appropriately.
    // abort() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development.
    NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
    abort();
  }
    
  return _persistentStoreCoordinator;
}


- (NSManagedObjectContext *)managedObjectContext {
  // Returns the managed object context for the application (which is already bound to the persistent store coordinator for the application.)
  if (_managedObjectContext != nil) {
    return _managedObjectContext;
  }
    
  NSPersistentStoreCoordinator *coordinator = [self persistentStoreCoordinator];
  if (!coordinator) {
    return nil;
  }
  
  _managedObjectContext = [[NSManagedObjectContext alloc] initWithConcurrencyType:NSMainQueueConcurrencyType];
  
  /*_managedObjectContext = [[NSManagedObjectContext alloc] initWithConcurrencyType:NSPrivateQueueConcurrencyType];
  [_managedObjectContext performBlockAndWait:^{
    [_managedObjectContext setPersistentStoreCoordinator:coordinator];
    [_managedObjectContext setMergePolicy:NSMergeByPropertyObjectTrumpMergePolicy];
  }];*/
  
  [_managedObjectContext setPersistentStoreCoordinator:coordinator];
  [_managedObjectContext setRetainsRegisteredObjects:YES];
  return _managedObjectContext;
}

#pragma mark - Core Data Saving support

- (void)saveContext {
    NSManagedObjectContext *managedObjectContext = self.managedObjectContext;
    if (managedObjectContext != nil) {
        NSError *error = nil;
        if ([managedObjectContext hasChanges] && ![managedObjectContext save:&error]) {
            // Replace this implementation with code to handle the error appropriately.
            // abort() causes the application to generate a crash log and terminate. You should not use this function in a shipping application, although it may be useful during development.
            NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
            abort();
        }
    }
}

- (NSManagedObjectContext*) getMocObject
{
  NSManagedObjectContext* pMoc = [[NSManagedObjectContext alloc] initWithConcurrencyType:NSPrivateQueueConcurrencyType];

  
  [pMoc setPersistentStoreCoordinator:_persistentStoreCoordinator];
  [pMoc setRetainsRegisteredObjects:YES];
  return pMoc;
}

//db functions
#pragma mark Core Date insert operation
/*-(BOOL) updateGoalData:(NSInteger)nBodyId data:(float)fValue unitTppe:(short)nType
{
    N_DataGoals* pGoalData = [self loadGoalData:nBodyId from:nil to:nil unitTppe:nType last:YES];
    if(pGoalData == nil)
        return NO;
    pGoalData.dataValue = [NSNumber numberWithFloat:fValue];
    pGoalData.unitType = [NSNumber numberWithShort:nType];
 
    if (![_managedObjectContext save:&error]) {
        NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
        UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
        [alertView show];
        //[alertView release];
        return NO;
    }
    return YES;
}*/

- (NSInteger) getNextGoalId
{
  if(![self isNetWorkConnAvailable])
    return -1;
  
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  NSInteger nNextId = 0;//[userSetting integerForKey:kNext_GoalId];
  if(nNextId > 0) {
    nNextId++;
    [userSetting setInteger:nNextId forKey:kNext_GoalId];
    return nNextId;
  }
  
  NSDictionary *measInfo = @{
                             @"BodyId" : [NSString stringWithFormat:@"%ld", (long)_nLoginBodyId],
                             @"hType" : @"255"
                             };
  
  NSString* sUrl = @"Host";
  NSMutableURLRequest *request = [self requestWebApiRouter:@"POST" url:sUrl data:measInfo];
  
  
  // 6.同步发送请求
  //[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
  NSData *data= [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
  if (data != nil) {
    NSString* sRecv = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
    sRecv = [sRecv substringWithRange: NSMakeRange(1, sRecv.length-2)];
    nNextId = (NSInteger)sRecv.integerValue;
    [userSetting setInteger:nNextId forKey:kNext_GoalId];
  }
  return nNextId;
}

- (NSUInteger) getHrateRcdCount
{
  if(!_bIniCoreData)
    [self initCoreData];
  
  NSFetchRequest *request = _request;//[[NSFetchRequest alloc] init];
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_Rate" inManagedObjectContext:managedObjectContext];
  [request setEntity:entity];
  //[NSFetchRequest fetchRequestWithEntityName:@"H_Rate"];
  //[request setPropertiesToFetch:[NSArray arrayWithObject:@"hRateId"]];
  request.fetchLimit = 0;
  
  [request setIncludesSubentities:NO]; //Omit subentities. Default is YES (i.e. include subentities)

  NSPredicate *predicate = [NSPredicate predicateWithFormat:@"bodyId>=0"];
  [request setPredicate:predicate];
  
  //NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"hRateId" ascending:YES];
  //NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  //[request setSortDescriptors:sortDescriptors];
  [request setSortDescriptors:nil];
  
  NSError *err;
  //NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&err] mutableCopy];
  NSUInteger nCount = [managedObjectContext countForFetchRequest:request error:&err];
  //if(nCount == NSNotFound) {
    //return 0;
  //}
  //NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  //[userSetting setInteger:nCount forKey:kCount_HRate];
  
  return nCount;
  //[request release];
}

- (N_DataGoals*) saveGoalData:(NSInteger)nBodyId data:(float)fValue dvUn:(short) nUn unitType:(short)nType toSvr:(BOOL)bToSvr
{
  NSInteger nId = 0;
  if(![self isNetWorkConnAvailable]) {
    nId = -1;
    [self showAlertBox:NSLocalizedString(@"WAN Network", nil) msg:NSLocalizedString(@"NO any WAN network connection, no function", nil)];
    return nil;
  }
  
  N_DataGoals* pGoalData = [self loadGoalData:nBodyId from:nil to:nil unitType:nType last:YES];
  if(pGoalData == nil) {
    nId = [self getNextGoalId];
    
    pGoalData = (N_DataGoals*)[NSEntityDescription insertNewObjectForEntityForName:@"N_DataGoals" inManagedObjectContext:_managedObjectContext];
    pGoalData.goalId = [NSNumber numberWithInteger: nId];
  }
  pGoalData.bodyId = [NSNumber numberWithInteger:nBodyId];
  pGoalData.goalOn = [NSNumber numberWithBool:YES];
    
  pGoalData.dataValue = [NSNumber numberWithFloat:fValue];
  pGoalData.valUnit = [NSNumber numberWithShort: nUn];
  pGoalData.unitType = [NSNumber numberWithShort:nType];
  pGoalData.goalDate = [NSDate date];
    
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(NSLocalizedString(@"OK", nil), nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return nil;
  }
  
  NSString* sGoalVal = [NSString stringWithFormat:@"%f", fValue];
  NSString* sValUnit = [NSString stringWithFormat:@"%i", nUn];
  NSString* sUnitType = [NSString stringWithFormat:@"%i", nType];
  
  if(bToSvr && nId >= 0)
    [self sendGoalDataToSvr:-1 body:nBodyId data:sGoalVal uType:sValUnit oType:sUnitType];
  return pGoalData;
}


- (void) storeRegGoalData:(float)fGoalWgt wun:(int) nWu dist:(float)fDist dun:(int)nDu step:(NSInteger)nSteps maxBpm:(int)nMaxBpm minBpm:(int)nMinBpm;
{
  NSInteger nBodyId = _bodyInfo.m_nBodyId;
  [self saveGoalData:nBodyId data:fGoalWgt dvUn:nWu unitType:11 toSvr:NO];
  [self saveGoalData:nBodyId data:fDist dvUn:nDu unitType:12 toSvr:NO];
  [self saveGoalData:nBodyId data:nSteps dvUn:0 unitType:13 toSvr:NO];
  [self saveGoalData:nBodyId data:nMaxBpm dvUn:0 unitType:14 toSvr:NO];
  //[self saveGoalData:nBodyId data:nMinBpm dvUn:0 unitType:15 toSvr:NO];
}

- (void) setUserMgr:(int)nMgr admin:(NSInteger)nClubAdmin
{
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  [userSetting setInteger:nMgr forKey:kReg_UserMgr];
  [userSetting setInteger:nClubAdmin forKey:kReg_ClubAdmin];
}

- (BOOL) isUserMgr
{
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  NSInteger nMgr = [userSetting integerForKey:kReg_UserMgr];
  NSInteger nAdmin = [userSetting integerForKey:kReg_ClubAdmin];
  return nMgr == 1 || nAdmin > 0;
}

- (N_DataGoals*) loadGoalData:(NSInteger)nBodyId from:(NSDate*)sFr to:(NSDate*)sTo unitType:(short)nType last:(BOOL)bLast
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
    if(!_bIniCoreData)
        [self initCoreData];
    if(_maCoreData != nil)
        [_maCoreData removeAllObjects];
    
    NSError *error = nil;
    NSManagedObjectContext* managedObjectContext = _managedObjectContext;
    //NSFetchRequest *request = [[NSFetchRequest alloc] init];
    NSFetchRequest *request = _request;
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_DataGoals" inManagedObjectContext:managedObjectContext];
    //NSPredicate *predicate;
    [request setEntity:entity];
    request.fetchLimit = bLast? 1: 0;
    
    NSPredicate *predicate = nil;
    if(sFr != nil && sTo != nil) {
        if(nType > 0)
            predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND goalDate>%@ AND goalDate<%@ AND unitType=%i", nBodyId, sFr, sTo, nType];
        else
            predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND goalDate>%@ AND goalDate<%@", nBodyId, sFr, sTo];
    }
    else {
        if(nType > 0)
            predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND unitType=%i", nBodyId, nType];
        else
            predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld", nBodyId];
    }
    [request setPredicate:predicate];
    
    // Order the events by creation date, most recent first.
    NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"goalId" ascending:(bLast?NO:YES)];
    NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
    [request setSortDescriptors:sortDescriptors];
    
    // Execute the fetch -- create a mutable copy of the result.
    NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
    if (mutableFetchResults == nil) {
        // Handle the error.
        NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
        UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
        [alertView show];
    }
    
    // Set self's events array to the mutable array, then clean up.
    _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
    
    N_DataGoals* nGoal = nil;
    if(_maCoreData != nil && _maCoreData.count > 0)
        nGoal = [_maCoreData objectAtIndex:0];
        
    
    //[request setPropertiesToFetch: nil];
    return nGoal;
}

- (NSInteger) getNextWgtId
{
  if(![self isNetWorkConnAvailable])
    return -1;
  /*NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_WgtData" inManagedObjectContext:managedObjectContext];
  [request setEntity:entity];
  [request setFetchLimit:1];
  
  NSPredicate *predicate = [NSPredicate predicateWithFormat:@"nBodyId>%@", @"0"];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"measId" ascending:NO];
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *maRcdset = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  [request setFetchLimit:0];
  if (maRcdset == nil  || maRcdset.count == 0) {
    return 1;
  }
  N_WgtData* nRndRcd = (N_WgtData*)[maRcdset objectAtIndex:0];
  NSInteger nNextId = nRndRcd.measId.integerValue;
  return nNextId + 1;*/
  
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  NSInteger nNextId = 0; //[userSetting integerForKey:kNext_WgtId];
  /*if(nNextId > 0) {
    nNextId++;
    [userSetting setInteger:nNextId forKey:kNext_WgtId];
    return nNextId;
  }*/
  
  NSDictionary *measInfo = @{
                             @"BodyId" : [NSString stringWithFormat:@"%ld", (long)_nLoginBodyId],
                             @"hType" : @"41"
                             };
  
  NSString* sUrl = @"Host";
  NSMutableURLRequest *request = [self requestWebApiRouter:@"POST" url:sUrl data:measInfo];
  
  
  // 6.同步发送请求
  //[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
  NSData *data= [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
  if (data != nil) {
    NSString* sRecv = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
    sRecv = [sRecv substringWithRange: NSMakeRange(1, sRecv.length-2)];
    nNextId = (NSInteger)sRecv.integerValue;
    [userSetting setInteger:nNextId forKey:kNext_WgtId];
  }
  return nNextId;
}

- (N_WgtData *) insertWgtData:(NSString*)sn card:(NSString*)cn data:(float)fData unit:(short)iUnit
                       bodyId:(NSInteger)nBodyId dtScale:(NSString*) sTime iOStime: (Boolean) bOsTime toSvr:(BOOL)bToSvr
{
  NSInteger nMeasId = [self getNextWgtId];
  N_WgtData *nWgtData = (N_WgtData *)[NSEntityDescription insertNewObjectForEntityForName:@"N_WgtData" inManagedObjectContext:_managedObjectContext];
    
  //body ID
  //NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  //NSString* sBodyId = [userSetting stringForKey:kBodyIdStr]
    
    //int n = [sTime length];
  if([sTime hasSuffix:@"\r\n"])
    sTime = [sTime stringByReplacingOccurrencesOfString:@"\r\n" withString:@" +0000"];
  else if([sTime hasSuffix:@"\0"])
    sTime = [sTime stringByReplacingOccurrencesOfString:@"\0" withString:@""];
  //n = [sTime length];
    
  NSString* sInitDtFmt = _dtFmt.dateFormat;
  NSDateFormatter* dtFormater = _dtFmt;
  NSString *sMeasTime = [NSString stringWithString:sTime];
  //const char* szTime = [sMeasTime UTF8String];
  if(bOsTime) {
    if([sTime hasSuffix:@"+0000"]) {
      [dtFormater setDateFormat:@"yyyy-MM-dd HH:mm:ss Z"];
      //[dtFormater setTimei:[NSTimeZone timeZoneWithName:@"CDT"]];
    }
    else {
      [dtFormater setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
    }
  }
  else {
    [dtFormater setDateFormat:@"MM/dd/yy HH:mm:ss"];
  }
  NSDate* dtWgt = [dtFormater dateFromString: sMeasTime];
  if (dtWgt == nil) {
    if(bOsTime)
      [dtFormater setDateFormat:@"MM/dd/yyyy HH:mm:ss"];
    else
      [dtFormater setDateFormat:@"MM/dd/yy HH:mm:ss"];
    dtWgt = [dtFormater dateFromString: sMeasTime];
  }
  if (dtWgt == nil)
    dtWgt = [NSDate date];
  
  if (bOsTime) {
    nWgtData.iOsDateTime = [NSDate date];
    nWgtData.scaDateTime = [NSDate date];
  }
  else {
    nWgtData.iOsDateTime = dtWgt;
    nWgtData.scaDateTime = dtWgt;
  }
    
  nWgtData.measId = [NSNumber numberWithInteger:nMeasId];
  nWgtData.isnScale = sn;
  nWgtData.mWgtData = [NSNumber numberWithFloat:fData];
  nWgtData.mWgtUnit = [NSNumber numberWithShort:iUnit]; //1 kg, 2 lb
  nWgtData.nBodyId = [NSNumber numberWithInteger:nBodyId];
  //nWgtData.scaDateTime = dtWgt;
    
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return NULL;
  }
  else {
    [self refreshCoreDataItems:nWgtData];
  }
    
  [_dtFmt setDateFormat:sInitDtFmt];
  
  //sent to server
  if(bToSvr && nMeasId > 0)
    [self sendWfbsDataToSvr:nBodyId measId:nMeasId sn:sn wgt:fData wu:iUnit measTime:dtWgt
                        fat:0.0 wat:0.0 hgt:0.0 hu:0 oth:0
                        bph:0 bpl:0 hrt:0
                        stp:0 dist:0.0 calory:0.0 type:0];
  return nWgtData;
}

- (NSInteger) insertWiFiWgtData: (NSInteger)nMeasId DevId:(NSString*)sn card:(NSString*)cn data:(float)fData unit:(short)iUnit
                         bodyId:(NSInteger)nBodyId dtScale:(NSString*)sTime
{
  N_WgtData *nWgtData = (N_WgtData *)[NSEntityDescription insertNewObjectForEntityForName:@"N_WgtData" inManagedObjectContext:_managedObjectContext];
  
  //int n = [sTime length];
  if([sTime hasSuffix:@"\r\n"])
    sTime = [sTime stringByReplacingOccurrencesOfString:@"\r\n" withString:@" +0000"];
  else if([sTime hasSuffix:@"\0"])
    sTime = [sTime stringByReplacingOccurrencesOfString:@"\0" withString:@""];
  //n = [sTime length];
  
  NSString* sInitDtFmt = _dtFmt.dateFormat;
  NSDateFormatter* dtFormater = _dtFmt;
  NSString *sMeasTime = [NSString stringWithString:sTime];
  //const char* szTime = [sMeasTime UTF8String];
  [dtFormater setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
  NSDate* dtWgt = [dtFormater dateFromString: sMeasTime];

  if (dtWgt == nil)
    dtWgt = [NSDate date];
  nWgtData.iOsDateTime = dtWgt;
  nWgtData.scaDateTime = dtWgt;

  
  nWgtData.measId = [NSNumber numberWithInteger:nMeasId];
  nWgtData.isnScale = sn;
  nWgtData.mWgtData = [NSNumber numberWithFloat:fData];
  nWgtData.mWgtUnit = [NSNumber numberWithShort:iUnit]; //1 kg, 2 lb
  nWgtData.nBodyId = [NSNumber numberWithInteger:nBodyId];
  //nWgtData.scaDateTime = dtWgt;
  
  [_dtFmt setDateFormat:sInitDtFmt];
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return -1;
  }
  else {
    [self refreshCoreDataItems:nWgtData];
  }
   return nMeasId;
}

- (BOOL) insertSyncWgtData:(NSNumber*)nMeasId dtScale:(NSString*)sTime sn:(NSString*)sSn data:(NSNumber*)nWgtVal unit:(NSNumber*)nUnit
{
  N_WgtData *nWgtData = (N_WgtData *)[NSEntityDescription insertNewObjectForEntityForName:@"N_WgtData" inManagedObjectContext:_managedObjectContext];
  
  NSString* sInitDtFmt = _dtFmt.dateFormat;
  [_dtFmt setDateFormat:@"MM/dd/yyyy HH:mm:ss"];
                                  
  nWgtData.measId = nMeasId;
  nWgtData.nBodyId = [NSNumber numberWithInteger:_bodyInfo.m_nBodyId];
  nWgtData.iOsDateTime = [_dtFmt dateFromString:sTime];
  nWgtData.scaDateTime = [_dtFmt dateFromString:sTime];
  nWgtData.mWgtData = nWgtVal;
  nWgtData.mWgtUnit = nUnit;
  
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return NO;
  }
  else {
    [self refreshCoreDataItems:nWgtData];
  }
                                  
  [_dtFmt setDateFormat:sInitDtFmt];
  return YES;
}

- (NSInteger) getNextFatId
{
  if(![self isNetWorkConnAvailable])
    return -1;
  /*NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_FatData" inManagedObjectContext:managedObjectContext];
  [request setEntity:entity];
  [request setFetchLimit:1];
  
  NSPredicate *predicate = [NSPredicate predicateWithFormat:@"bodyId>%@", @"0"];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"measId" ascending:NO];
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *maRcdset = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  [request setFetchLimit:0];
  if (maRcdset == nil  || maRcdset.count == 0) {
    return 1;
  }
  N_FatData* nRndRcd = (N_FatData*)[maRcdset objectAtIndex:0];
  NSInteger nNextId = nRndRcd.measId.integerValue;
  return nNextId + 1;*/
  
  NSInteger nNextId = 0; 
  NSDictionary *measInfo = @{
                             @"BodyId" : [NSString stringWithFormat:@"%ld", (long)_nLoginBodyId],
                             @"hType" : @"42"
                             };
  
  NSString* sUrl = @"Host";
  NSMutableURLRequest *request = [self requestWebApiRouter:@"POST" url:sUrl data:measInfo];
  
  
  // 6.同步发送请求
  //[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
  NSData *data= [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
  if (data != nil) {
    NSString* sRecv = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
    sRecv = [sRecv substringWithRange: NSMakeRange(1, sRecv.length-2)];
    nNextId = (NSInteger)sRecv.integerValue;
  }
  return nNextId;
}

- (N_FatData *) insertFatData:(NSInteger)nBodyId fat:(float)fatVal wat:(float)watVal
                          hgt:(float)bodyHgt unit:(short)hUn oth:(long long)nOth date:(NSDate*)dtMeas toSvr:(BOOL)bToSvr
{
  //form next ID
  NSInteger nId = [self getNextFatId];
  //return nil;
    
  // NSInteger nId = fatArray.count + 1;
  
  N_FatData *nFatData = (N_FatData *)[NSEntityDescription insertNewObjectForEntityForName:@"N_FatData" inManagedObjectContext:_managedObjectContext];
    
  nFatData.measId = [NSNumber numberWithInteger:nId];
  nFatData.bodyId = [NSNumber numberWithInteger:nBodyId];
  nFatData.fatVal = [NSNumber numberWithFloat:fatVal];
  nFatData.watVal = [NSNumber numberWithFloat:watVal];
  nFatData.bodyHgt = [NSNumber numberWithFloat:bodyHgt];
  nFatData.hgtUnit = [NSNumber numberWithShort:hUn];
  nFatData.othData = [NSNumber numberWithLongLong:nOth];
  nFatData.measDate = dtMeas;
  nFatData.serialNo = @"Ble-FatWat";
    
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return NULL;
  }
  else {
    [self refreshCoreDataItems:nFatData];
  }
  
  if(bToSvr && nId > 0)
    [self sendWfbsDataToSvr:nBodyId measId:nId sn:@"" wgt:0.0 wu:0 measTime:dtMeas
                        fat:fatVal wat:watVal hgt:bodyHgt hu:hUn oth:nOth
                        bph:0 bpl:0 hrt:0
                        stp:0 dist:0.0 calory:0.0 type:1];
    return nFatData;
}

- (BOOL) insertSyncFatData:(NSNumber*)nMeasId date:(NSString*)sTime fat:(NSNumber*)nFat wat:(NSNumber*)nWat
{
  N_FatData *nFatData = (N_FatData *)[NSEntityDescription insertNewObjectForEntityForName:@"N_FatData" inManagedObjectContext:_managedObjectContext];
  NSString* sInitDtFmt = _dtFmt.dateFormat;
  [_dtFmt setDateFormat:@"MM/dd/yyyy HH:mm:ss"];
  
  nFatData.measId = nMeasId;
  nFatData.bodyId = [NSNumber numberWithInteger:_bodyInfo.m_nBodyId];
  nFatData.fatVal = nFat;
  nFatData.watVal = nWat;
  nFatData.bodyHgt = [NSNumber numberWithFloat:0];
  nFatData.hgtUnit = [NSNumber numberWithShort:0];
  nFatData.othData = [NSNumber numberWithLongLong:0];
  nFatData.measDate = [_dtFmt dateFromString:sTime];
  nFatData.serialNo = @"BleSync-FatWat";
  
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return NO;
  }
  else {
    [self refreshCoreDataItems:nFatData];
  }
  
  [_dtFmt setDateFormat:sInitDtFmt];
  return YES;
  
}

- (BOOL) detectPhoneCall
{
  __block BOOL bCellCallRtn = YES;
  _callCenter.callEventHandler = ^(CTCall* call) {
    if ([call.callState isEqualToString:CTCallStateDisconnected])
    {
      NSLog(@"Call has been disconnected");
    }
    else if ([call.callState isEqualToString:CTCallStateConnected])
    {
      NSLog(@"Call has just been connected");
      _bCellCallConn = YES;
    }
    else if([call.callState isEqualToString:CTCallStateIncoming])
    {
      NSLog(@"Call is incoming");
    }
    else if ([call.callState isEqualToString:CTCallStateDialing])
    {
      NSLog(@"call is dialing");
      _bCellCallConn = YES;
    }
    else
    {
      NSLog(@"Nothing is done");
    }
    bCellCallRtn = YES;
  };
  
  return bCellCallRtn;

  /*CTCallCenter *callCenter = [[CTCallCenter alloc] init];
  callCenter.callEventHandler:^(CTCall * call) {
    if (call.callState == CTCallStateDisconnected)
    {
      //NSLog(@"Call has been disconnected");
      //self.viewController.signalStatus=YES;
      return NO;
    }
    else if (call.callState == CTCallStateConnected)
    {
      //NSLog(@"Call has just been connected");
      return YES;
    }
    
    else if(call.callState == CTCallStateIncoming)
    {
      //NSLog(@"Call is incoming");
      //self.viewController.signalStatus=NO;
      return NO;
    }
    
    else if (call.callState ==CTCallStateDialing)
    {
      //NSLog(@"call is dialing");
      return YES;
    }
    else
    {
      //NSLog(@"Nothing is done");
      return NO;
    }
  };
  return NO;*/
}

- (void) ctCallStateDidChange:(NSNotification *)notification
{
  NSString *callInfo = [[notification userInfo] objectForKey:@"callState"];
  if ([callInfo isEqualToString:CTCallStateDisconnected]) {
    NSLog(@"before show");
    //[self.view viewWithTag:kNONEMERGENCYCALLSAVEDTOLOG_TAG].hidden = NO;
    NSLog(@"after show");
  }
}

- (NSInteger) getNextHrateId:(BOOL)bToSvr
{
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  [userSetting synchronize];
  
  NSInteger nRcdCount = [userSetting integerForKey:kCount_HRate];
  //NSInteger nNextIdStore = [userSetting integerForKey:kNext_HrateId];
  //if(!bToSvr)
    //return -nNextIdStore - 1;
  
  NSInteger nNextId = 0;
  //if(nNextIdStore != 0) {
    //nNextId = nNextIdStore;
  //}
  if(nRcdCount == 0) {
    nNextId = [self getHrateRcdCount];
    //[userSetting setInteger:nNextId forKey:kCount_HRate];
  }
  else {
    nNextId = nRcdCount;
  }
  nNextId++;

  [userSetting setInteger:nNextId forKey:kCount_HRate];
  [userSetting synchronize];
  
  BOOL bNetConn = [self isNetWorkConnAvailable];
  if(!bNetConn && bToSvr) {
    //nNextId = [userSetting kCount_HRate];
    /*if(nNextId == 0) {
      nNextId = [userSetting integerForKey:kNext_HrateId];
      nNextId++;
      
      [userSetting setInteger:nNextId forKey:kCount_HRate];
      [userSetting synchronize];
    }
    
    [userSetting setInteger:nNextId forKey:kNext_HrateId];
    [userSetting synchronize];
    [userSetting synchronize];*/
    
    return -nNextId;
  }
  
  if(bToSvr) {
    nNextId = 0;//[userSetting integerForKey:kNext_HrateId];
  }
  else {
    return -nNextId;
  }
  
  /*if(nNextId > 0) {
    //nNextId++;
    [userSetting setInteger:nNextId forKey:kNext_HrateId];
    [userSetting synchronize];
    return nNextId;
  }*/
  
  //CTCallCenter* pcellPhone = [CTCellCenter]
    
    /*NSError *error = nil;
    NSManagedObjectContext* managedObjectContext = _managedObjectContext;
    NSFetchRequest *request = _request;
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_Rate" inManagedObjectContext:managedObjectContext];
    [request setEntity:entity];
    [request setFetchLimit:1];
    
    NSPredicate *predicate = [NSPredicate predicateWithFormat:@"bodyId>%@", @"0"];
    [request setPredicate:predicate];
    
    // Order the events by creation date, most recent first.
    NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"hRateId" ascending:NO];
    NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
    [request setSortDescriptors:sortDescriptors];
    
    
    // Execute the fetch -- create a mutable copy of the result.
    NSMutableArray *maRcdset = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
    [request setFetchLimit:0];
    if (maRcdset == nil  || maRcdset.count == 0) {
        return 1;
    }
    H_Rate* nRndRcd = (H_Rate*)[maRcdset objectAtIndex:0];
    nNextId = nRndRcd.hRateId.integerValue + 1;
  
  [userSetting setInteger:nNextId forKey:kNext_HrateId];
  return nNextId;*/
  
  [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(ctCallStateDidChange:) name:@"CTCallStateDidChange" object:nil];
  /*_bCellCallConn = NO;
  BOOL bRtnVal = [self detectPhoneCall];
  while(_b4GNetConn && !bRtnVal) {
    bRtnVal = [self detectPhoneCall];
  }
  if(_bCellConn && _b4GNetConn)
    return -nNextId;*/
  
  NSDictionary *measInfo = @{
    @"BodyId" : [NSString stringWithFormat:@"%ld", (long)_bodyInfo.m_nBodyId],
    @"hType" : @"3"
  };
  
  NSString* sUrl = @"Host";
  NSMutableURLRequest *request = [self requestWebApiRouter:@"POST" url:sUrl data:measInfo];
  
  
  // 6.同步发送请求
  //Connection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
  NSData *data= [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
  if (data != nil) {
    NSString* sRecv = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
    sRecv = [sRecv substringWithRange: NSMakeRange(1, sRecv.length-2)];
    nNextId = (NSInteger)sRecv.integerValue;
    [userSetting setInteger:nNextId forKey:kNext_HrateId];
  }
  return nNextId;
}

- (H_Rate*) loadHrateStartRcd:(NSInteger)nBodyId  start: (NSDate*)dtStart
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //[managedObjectContext reset];
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_Rate" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = 1;
  
  NSPredicate *predicate = [NSPredicate predicateWithFormat:@"hEnterDate=%@", dtStart];
  if(predicate == nil)
    return nil;
  
  [request setPredicate:predicate];
  [request setSortDescriptors:nil];
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if (mutableFetchResults == nil) {
    // Handle the error.
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
  }
  
  // Set self's events array to the mutable array, then clean up.
  _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
  if(_maCoreData.count > 0) {
    H_Rate* pRate = [_maCoreData objectAtIndex:0];
    return pRate;
  }
  else {
    return nil;
  }
}

- (H_Rate*) insertHrateData:(BOOL)bSureNew bodyId:(NSInteger)nBodyId hrateId:(NSInteger*) pHrateId time:(NSDate*)dtStart toSvr:(BOOL)bToSvr
{
  H_Rate *pHrate = nil;
  if(!bSureNew && !bToSvr) {
    if([self checkExistsHrateStart:nBodyId start:dtStart]) {
      pHrate = [self loadHrateStartRcd:nBodyId start:dtStart];
      *pHrateId = 0; //pHrate.hRateId.integerValue;
      pHrate.nSyncType = [NSNumber numberWithInteger:(bToSvr?0:2)];
    
    //test
    //NSInteger nHrateId = pHrate.hRateId.integerValue;
    //NSInteger nLastIdx = pHrate.nLastUpdIdx.integerValue;
    //test
    
    [self refreshCoreDataItems:pHrate];
    return pHrate;
  }
  else {
    NSDate* dtBegin = [dtStart dateByAddingTimeInterval:-2];
    if([self checkExistsHrateStart:nBodyId start:dtBegin]) {
      pHrate = [self loadHrateStartRcd:nBodyId start:dtStart];
      *pHrateId = 0; //pHrate.hRateId.integerValue;
      pHrate.nSyncType = [NSNumber numberWithInteger:(bToSvr?0:2)];
      return pHrate;
    }
  }
  
    if(!bToSvr) {
      [_managedObjectContext reset];
      pHrate = [self isDurHrateItemDateRow:nBodyId measTime:dtStart];
      if(pHrate != nil) {
        //NSDate* dtMeas = pHrate.hEnterDate;
        //pHrate = [self loadHrateStartRcd:nBodyId start:pHrate.hEnterDate];
        //if(pHrate != nil) {
        *pHrateId = 1; //pHrate.hRateId.integerValue;
        pHrate.nSyncType = [NSNumber numberWithInteger:2];
      
        //test
        //NSInteger nHrateId = pHrate.hRateId.integerValue;
        //NSInteger nLastIdx = pHrate.nLastUpdIdx.integerValue;
        //test
      
        [self refreshCoreDataItems:pHrate];
        return pHrate;
      //}
      }
    }
  }
  //NSInteger nId = fatArray.count + 1;
  NSInteger nId = [self getNextHrateId: bToSvr];
  if(bToSvr && nId > 0) {
    [self sendHrateDataToSvr:nId bodyId:nBodyId measId:0 itemId:0 rateIdx:0 rngTxt:@"" measVal:0
                           cal:0.0 dur:0.0 dateTxt:@"" montxt:@"" time:dtStart type:0];
  }
  
  NSManagedObjectContext* pMoc = _managedObjectContext;//[self getMocObject];
  pHrate = (H_Rate *)[NSEntityDescription insertNewObjectForEntityForName:@"H_Rate" inManagedObjectContext:pMoc];
  //if (nBodyId == 0)
    //sBodyId = @"0";
    
  pHrate.hRateId = [NSNumber numberWithInteger:nId];
  //nHrate.bodyId = [NSNumber numberWithInteger:nBodyId];
  pHrate.bodyId = [NSNumber numberWithInteger:nBodyId];
  pHrate.hEnterDate = dtStart;//[NSDate date];
  pHrate.bMemory = [NSNumber numberWithBool:!bToSvr];
  
  //pHrate.bUpdOk = [NSNumber numberWithBool:bToSvr];
  BOOL bNetOk = [self isNetWorkConnAvailable]; //nId > 0;
  pHrate.nLastUpdIdx = [NSNumber numberWithInteger:bNetOk?(bToSvr?-1:0):-2];
  pHrate.nSyncType = [NSNumber numberWithInteger:(bToSvr?0:2)];
  
  NSError *error = nil;
  if (![pMoc save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return nil;
  }
  else {
    //[self refreshCoreDataItems:pHrate];
    [pMoc refreshObject:pHrate mergeChanges:YES];
  }
  
  *pHrateId = nId;
  return pHrate;
}

- (BOOL) checkExistsHrateStart:(NSInteger)nBodyId start:(NSDate*)dtStart
{
  NSFetchRequest *request = [[NSFetchRequest alloc] initWithEntityName:@"H_Rate"];
  request.predicate = [NSPredicate predicateWithFormat:@"bodyId==%ld && hEnterDate==%@ && hRateId<%ld", (long)nBodyId, dtStart, (long)0];
  request.sortDescriptors = @[[NSSortDescriptor sortDescriptorWithKey:@"hRateId" ascending:NO]];
  NSArray *results = [_managedObjectContext executeFetchRequest:request error:nil];
  return results.count > 0;
}

- (BOOL) checkExistsHrateRcd:(NSInteger)nBodyId hrateId:(NSInteger)nHrateId
{
  NSFetchRequest *request = [[NSFetchRequest alloc] initWithEntityName:@"H_Rate"];
  request.predicate = [NSPredicate predicateWithFormat:@"bodyId==%ld && hRateId==%ld", (long)nBodyId, (long)nHrateId];
  request.sortDescriptors = nil;
  NSArray *results = [_managedObjectContext executeFetchRequest:request error:nil];
  return results.count > 0;
}

- (BOOL) checkExistsHrateTimeRcd:(NSInteger)nBodyId hrateId:(NSInteger)nHrateId time:(NSDate*) dtStart
{
  NSFetchRequest *request = [[NSFetchRequest alloc] initWithEntityName:@"H_Rate"];
  request.predicate = [NSPredicate predicateWithFormat:@"bodyId==%ld && hRateId==%ld && hEnterDate!=%@", (long)nBodyId, (long)nHrateId, dtStart];
  request.sortDescriptors = nil;
  NSArray *results = [_managedObjectContext executeFetchRequest:request error:nil];
  return results.count > 0;
}

- (void) updateSvrHrateId:(NSInteger)nBodyId oldId:(NSInteger)nOldId newId:(NSInteger)nNewId
{
  [self sendHrateDataToSvr:nOldId bodyId:nBodyId measId:nNewId itemId:0 rateIdx:0 rngTxt:@"" measVal:0
                       cal:0.0 dur:0.0 dateTxt:@"" montxt:@"" time:[NSDate date] type:9];
  
}

- (BOOL) insertSyncHrateData:(NSInteger)nBodyId hrateId:(NSInteger)nHrateId start:(NSDate*)dtStart end:(NSDate*)dtEnd mem:(BOOL)bMem act:(short)nAct
{
  if([self checkExistsHrateRcd: nBodyId hrateId:nHrateId]) {
    //[self updHrateSyncState:nHrateId toId:nHrateId lastIdx:-1];
    return YES;
  }
  
  H_Rate *pHrate = (H_Rate *)[NSEntityDescription insertNewObjectForEntityForName:@"H_Rate" inManagedObjectContext:_managedObjectContext];
  pHrate.hRateId = [NSNumber numberWithInteger:nHrateId];
  pHrate.bodyId = [NSNumber numberWithInteger:nBodyId];
  pHrate.hEnterDate = dtStart;
  pHrate.hEndDate = dtEnd;
  pHrate.actType = [NSNumber numberWithInt:(int)nAct];
  pHrate.bMemory = [NSNumber numberWithBool:bMem];
  //pHrate.bUpdOk = [NSNumber numberWithBool:YES];
  pHrate.nLastUpdIdx = [NSNumber numberWithInteger:0];
  pHrate.nSyncType = [NSNumber numberWithInteger:1];
  
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return NO;
  }
  else {
    [self refreshCoreDataItems:pHrate];
  }

  return YES;
}

- (NSInteger) getNextHrtMeasId
{
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  NSInteger nNextId = [userSetting integerForKey:kNext_HrmMeasId];
  if(nNextId > 0) {
    nNextId++;
    [userSetting setInteger:nNextId forKey:kNext_HrmMeasId];
    return nNextId;
  }
  if(![self isNetWorkConnAvailable])
    return -1;
  
  NSDictionary *measInfo = @{
                             @"BodyId" : [NSString stringWithFormat:@"%ld", (long)_bodyInfo.m_nBodyId],
                             @"hType" : @"4"
                             };
  
  NSString* sUrl = @"Host";
  NSMutableURLRequest *request = [self requestWebApiRouter:@"POST" url:sUrl data:measInfo];
  
  
  // 6.同步发送请求
  //[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
  NSData *data= [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
  if (data != nil) {
    NSString* sRecv = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
    sRecv = [sRecv substringWithRange: NSMakeRange(1, sRecv.length-2)];
    nNextId = (NSInteger)sRecv.integerValue;
    [userSetting setInteger:nNextId forKey:kNext_HrmMeasId];
  }
  return nNextId;
}

-(H_RateRng *) insertHrateRngData:(NSInteger)nHrateId bodyId:(NSInteger)nBodyId idx:(short)nIdx rng:(NSString*)sRng
                              dur:(float)fMinute cal:(float)fCal dtVal:dtMeas toSvr:(BOOL)bToSvr
{
  if(!bToSvr)
    return nil;
  
  H_RateRng *nHrtRng = (H_RateRng *)[NSEntityDescription insertNewObjectForEntityForName:@"H_RateRng" inManagedObjectContext:_managedObjectContext];
    
  NSInteger nId = bToSvr?[self getNextHrtMeasId]: -1;
  
  nHrtRng.measId = [NSNumber numberWithInteger:nId];
  nHrtRng.hRateId = [NSNumber numberWithInteger:nHrateId];
  nHrtRng.bodyId = [NSNumber numberWithInteger:nBodyId];
  nHrtRng.rateIdx = [NSNumber numberWithInteger:nIdx];
  nHrtRng.rateRng = sRng;
  nHrtRng.durMinute = [NSNumber numberWithFloat:fMinute];
  nHrtRng.caloriesBurned = [NSNumber numberWithFloat: fCal];
  nHrtRng.startTime = dtMeas;
    
  NSString* sInitDtFmt = _dtFmt.dateFormat;
  NSDateFormatter* dtFmt = _dtFmt;
  [dtFmt setDateFormat:@"yy/MM/dd"];
  nHrtRng.sDateTxt = [dtFmt stringFromDate:dtMeas];
  [dtFmt setDateFormat:@"MM/yyyy"];
  nHrtRng.sMonthTxt = [dtFmt stringFromDate:dtMeas];
    
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return NULL;
  }
  else {
    [self refreshCoreDataItems:nHrtRng];
  }
  
  [_dtFmt setDateFormat:sInitDtFmt];
  
  //sent to server
  if(bToSvr && nId > 0)
    [self sendHrateDataToSvr:nHrateId bodyId:nBodyId measId:nId itemId:0 rateIdx:nIdx rngTxt:nHrtRng.rateRng measVal:0
                       cal:fCal dur:fMinute dateTxt:nHrtRng.sDateTxt montxt:nHrtRng.sMonthTxt time:dtMeas type:1];  
                  
  
  return nHrtRng;
}

- (NSInteger) getNextHrtItemId
{
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  NSInteger nNextId = [userSetting integerForKey:kNext_HrmItemId];
  if(nNextId > 0) {
    nNextId++;
    [userSetting setInteger:nNextId forKey:kNext_HrmItemId];
    return nNextId;
  }
  if(![self isNetWorkConnAvailable])
    return -1;
  
  NSDictionary *measInfo = @{
                             @"BodyId" : [NSString stringWithFormat:@"%ld", (long)_bodyInfo.m_nBodyId],
                             @"hType" : @"5"
                             };
  
  NSString* sUrl = @"Host";
  NSMutableURLRequest *request = [self requestWebApiRouter:@"POST" url:sUrl data:measInfo];
  
  
  // 6.同步发送请求
  //[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
  NSData *data= [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
  if (data != nil) {
    NSString* sRecv = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
    sRecv = [sRecv substringWithRange: NSMakeRange(1, sRecv.length-2)];
    nNextId = (NSInteger)sRecv.integerValue;
    [userSetting setInteger:nNextId forKey:kNext_HrmItemId];
  }
  return nNextId;
}

-(H_RateItem *) insertHrateItemData:(NSInteger)nHrateId bodyId:(NSInteger)nBodyId hRate:(short)nHrate dtime:(NSDate*)dtMeas toSvr:(BOOL)bToSvr
{
  if([self updateHrateItemRcd:nBodyId hrateId:nHrateId hRate:nHrate dtime:dtMeas])
    return nil;
    //form next ID
    //NSMutableArray* fatArray = [self loadSqliteHrateItem:@"0" from:nil to:nil sort:false];
    //if(fatArray == nil)
    //return nil;
    
  NSInteger nId = bToSvr?[self getNextHrtItemId]: 0;
  /*if(nId > 0) {
    int m = 1;
  }*/
    
  H_RateItem *nHrtData = (H_RateItem *)[NSEntityDescription insertNewObjectForEntityForName:@"H_RateItem" inManagedObjectContext:_managedObjectContext];
    
  nHrtData.hItemId = [NSNumber numberWithInteger:nId];
  nHrtData.hRateId = [NSNumber numberWithInteger:nHrateId];
  nHrtData.bodyId = [NSNumber numberWithInteger:nBodyId];
  nHrtData.hRateValue = [NSNumber numberWithShort:nHrate];
    
  nHrtData.hRateTime = dtMeas;//[NSDate date];
  //[_managedObjectContext performBlockAndWait:^ {
    NSError *error = nil;
    //_managedObjectContext.mergePolicy = NSMergeByPropertyObjectTrumpMergePolicy;
    if (![_managedObjectContext save:&error]) {
      NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
      UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
      [alertView show];
      //return NULL;
    }
    else {
      [self refreshCoreDataItems:nHrtData];
    }
  //}];
  
  //sent to server
  if(bToSvr && nId > 0)
    [self sendHrateDataToSvr:nHrateId bodyId:nBodyId measId:0 itemId:nId rateIdx:0 rngTxt:@"" measVal:nHrate 
                       cal:0.0 dur:0.0 dateTxt:@"" montxt:@"" time:dtMeas type:2];
   
  return nHrtData;
}

- (H_Rate*) isDurHrateItemDateRow:(NSInteger)nBodyId measTime:(NSDate*)dtMeas
{
  H_Rate* pHrate = nil;
  NSFetchRequest *request = _request;//[[NSFetchRequest alloc] init];
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_Rate" inManagedObjectContext:_managedObjectContext];
  [request setEntity:entity];

  
  //NSFetchRequest *request = [[NSFetchRequest alloc] initWithEntityName:@"H_Rate"];
  request.predicate = [NSPredicate predicateWithFormat:@"bodyId==%ld && hEnterDate<=%@ && hEndDate>%@ && nSyncType=%ld && hRateId<%ld", (long)nBodyId, dtMeas, dtMeas, (long)2, (long)0];
  request.sortDescriptors = @[[NSSortDescriptor sortDescriptorWithKey:@"hRateId" ascending:NO]];
  NSArray *results = [_managedObjectContext executeFetchRequest:request error:nil];
  BOOL bExists = results.count > 0;
  if(bExists) {
    pHrate = [results objectAtIndex:0];
    //pHrate = [self loadHrateStartRcd:nBodyId start:pHrate.hEnterDate];
    //dtMeas = pHrate.hEnterDate;
  }
  
  return pHrate;
}

- (BOOL) updateHrateItemRcd:(NSInteger)nBodyId hrateId:(NSInteger)nHrateId hRate:(short)nBpm dtime:(NSDate*)dtMeas
{
  NSFetchRequest *request = [[NSFetchRequest alloc] initWithEntityName:@"H_RateItem"];
  request.predicate = [NSPredicate predicateWithFormat:@"bodyId==%ld && hRateId==%ld && hRateTime==%@", nBodyId, nHrateId, dtMeas];
  request.sortDescriptors = @[[NSSortDescriptor sortDescriptorWithKey:@"hItemId" ascending:YES]];
  NSArray *results = [_managedObjectContext executeFetchRequest:request error:nil];
  if(results.count > 0) {
    NSBatchUpdateRequest *req = [[NSBatchUpdateRequest alloc] initWithEntityName:@"H_RateItem"];
    req.predicate = [NSPredicate predicateWithFormat:@"bodyId==%ld && hRateId=%ld && hRateTime==%@ && hRateValue!=%d", nBodyId, nHrateId, dtMeas, nBpm];
    req.propertiesToUpdate = @{@"hRateValue" : [NSNumber numberWithShort:nBpm]};
    req.resultType = NSUpdatedObjectsCountResultType;
    //NSBatchUpdateResult* res = (NSBatchUpdateResult *)[_managedObjectContext executeRequest:req error:nil];
    //NSLog(@"%@ HrateItem value sync updated", res.result);
    return YES;
  }
  else {
    return NO;
  }
}

- (H_RateItem *) insertSyncHrateItemData:(NSInteger)nBodyId hrateId:(NSInteger)nHrateId itemId:(NSInteger)nItemId hRate:(short)nHrate dtime:(NSDate*)dtMeas
{
  //check exists & update hrate value
  /*NSFetchRequest *request = [[NSFetchRequest alloc] initWithEntityName:@"H_RateItem"];
  request.predicate = [NSPredicate predicateWithFormat:@"bodyId==%ld && hRateId=%ld && hRateTime==%@", nBodyId, nHrateId, dtMeas];
  request.sortDescriptors = @[[NSSortDescriptor sortDescriptorWithKey:@"hItemId" ascending:YES]];
  NSArray *results = [_managedObjectContext executeFetchRequest:request error:nil];
  if(results.count > 0) {
    NSBatchUpdateRequest *req = [[NSBatchUpdateRequest alloc] initWithEntityName:@"H_RateItem"];
    req.predicate = [NSPredicate predicateWithFormat:@"bodyId==%ld && hRateId=%ld && hRateTime==%@", nBodyId, nHrateId, dtMeas];
    req.propertiesToUpdate = @{@"hRateValue" : [NSNumber numberWithShort:nHrate]};
    req.resultType = NSUpdatedObjectsCountResultType;
    NSBatchUpdateResult* res = (NSBatchUpdateResult *)[_managedObjectContext executeRequest:req error:nil];
    NSLog(@"%@ HrateData sync state updated", res.result);
    return nil;
  }*/
  if([self updateHrateItemRcd:nBodyId hrateId:nHrateId hRate:nHrate dtime:dtMeas])
    return nil;

  
  H_RateItem *nHrtData = (H_RateItem *)[NSEntityDescription insertNewObjectForEntityForName:@"H_RateItem" inManagedObjectContext:_managedObjectContext];
  
  nHrtData.bodyId = [NSNumber numberWithInteger:nBodyId];
  nHrtData.hRateId = [NSNumber numberWithInteger:nHrateId];
  nHrtData.hItemId = [NSNumber numberWithInteger:nItemId];
  
  nHrtData.hRateValue = [NSNumber numberWithShort:nHrate];
  nHrtData.hRateTime = dtMeas;
  
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return NULL;
  }
  else {
    [self refreshCoreDataItems:nHrtData];
  }
  
  return nHrtData;
}

//user mgr
- (short) getNextBodyUserIdx
{
  //NSNumber *max = [teams valueForKeyPath: @"@max.teamID"];
  //NSPredicate *p = [NSPredicate predicateWithFormat: @"%K == %@", @"teamID", max];
  //Team *team = [[teams filteredSetUsingPredicate: p] anyObject];
  
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_GroupInfo" inManagedObjectContext:managedObjectContext];
  [request setEntity:entity];
  [request setFetchLimit:1];
  
  NSPredicate *predicate = [NSPredicate predicateWithFormat:@"bodyId>%@", @"0"];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"userIdx" ascending:NO];
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *maRcdset = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  [request setFetchLimit:0];
  if (maRcdset == nil  || maRcdset.count == 0) {
    return 1;
  }
  //NSInteger nNextId = maRcdset.count;
  N_GroupInfo *nGrpUser = [maRcdset objectAtIndex:0];
  short nNextId = nGrpUser.userIdx.shortValue;
  return nNextId + 1;
  
}

- (N_GroupInfo *) insertMembGroupInfo:(NSInteger)nGrpId bodyId:(NSInteger)nBodyId sn:(NSString*)sSn card:(NSString*)sCard email:(NSString*)sEmail
                                chest:(NSString*)sChest waist:(NSString*)sWaist sex:(NSString*)sSex age:(NSString*)sBorn wgt:(NSString*)sWgt wun:(NSString*)sWun
                                hgt:(NSString*)sHgt hun:(NSString*)sHun isAhtlet:(NSString*) sAthlet;
{
  NSString* sInitDtFmt = _dtFmt.dateFormat;
  //if([AppDelegate isLanguageChines])
  if([sBorn rangeOfString:@"-"].location != NSNotFound)
    [_dtFmt setDateFormat:@"yyyy-MM-dd"];
  else
    [_dtFmt setDateFormat:@"MM/dd/yyyy"];
  
  if(_managedObjectContext == nil)
    return nil;
  
  short nUserIdx = (short)[self getNextBodyUserIdx];
  if(sEmail == nil) {
    
  }
  
  N_GroupInfo *nGroupInfo = (N_GroupInfo *)[NSEntityDescription insertNewObjectForEntityForName:@"N_GroupInfo" inManagedObjectContext:_managedObjectContext];
  if ([sBorn isEqualToString:@""])
    sBorn = @"1/1/1910";
  
  
  nGroupInfo.groupId = [NSNumber numberWithInteger:nGrpId];
  nGroupInfo.bodyId = [NSNumber numberWithInteger:nBodyId];
  nGroupInfo.userIdx = [NSNumber numberWithShort:nUserIdx];
  nGroupInfo.scaleNo = sSn;
  nGroupInfo.cardNo = sCard;
  nGroupInfo.bodyEmail = sEmail;
  //nGroupInfo.bodySex = [NSNumber numberWithBool:([sSex isEqualToString:@"1"]? YES: NO)];
  nGroupInfo.bodySex = [NSNumber numberWithShort:(short)sSex.intValue];
  nGroupInfo.bodyAge = [_dtFmt dateFromString:sBorn];
  
  nGroupInfo.fChest = [NSNumber numberWithFloat:sChest.floatValue];
  nGroupInfo.fWaist = [NSNumber numberWithFloat:sWaist.floatValue];
  
  nGroupInfo.bodyWgt = [NSNumber numberWithFloat:[sWgt floatValue]];
  nGroupInfo.wgtUnit = [NSNumber numberWithShort:(short)[sWun integerValue]];
  nGroupInfo.bodyHgt = [NSNumber numberWithFloat:[sHgt floatValue]];
  nGroupInfo.hgtUnit = [NSNumber numberWithShort:(short)[sHun integerValue]];
  //nGroupInfo.isAthlete = [NSNumber numberWithBool:([sAthlet isEqualToString:@"1"]? YES: NO)];
  nGroupInfo.athleteLvl = [NSNumber numberWithShort:[sAthlet intValue]];
  //nGroupInfo.sName = sName;
  
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return NULL;
  }
  else {
    [self refreshCoreDataItems:nGroupInfo];
    //[self initCoreData];
  }
  
  [_dtFmt setDateFormat:sInitDtFmt];
  return nGroupInfo;
}

- (BOOL) updateMembGroupInfo:(NSInteger)nBodyId sn:(NSString*)sSn card:(NSString*)sCardNo email:(NSString*)sName chest:(NSString*)sChest waist:(NSString*)sWaist
                         sex:(NSString*)sSex age:(NSString*)sBorn wgt:(NSString*)sWgt wun:(NSString*)sWun hgt:(NSString*)sHgt hun:(NSString*)sHun fitLvl:(NSString*)sAth
{
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_GroupInfo" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = 1;
  
  NSPredicate *predicate =  [NSPredicate predicateWithFormat:@"bodyId=%ld", (long)nBodyId];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  [request setSortDescriptors:nil];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  _request.fetchLimit = 0;
  if(mutableFetchResults != nil && mutableFetchResults.count > 0) {
    NSString* sInitDtFmt = _dtFmt.dateFormat;
    if([AppDelegate isLanguageChines])
      [_dtFmt setDateFormat:@"yyyy-MM-dd"];
    else
      [_dtFmt setDateFormat:@"MM/dd/yyyy"];
    
    N_GroupInfo* nGroupInfo = [mutableFetchResults objectAtIndex:0];

    nGroupInfo.scaleNo = sSn;
    if(![sCardNo isEqualToString:@"00000000"])
      nGroupInfo.cardNo = sCardNo;
    nGroupInfo.bodyEmail = sName;
    nGroupInfo.bodySex = [NSNumber numberWithShort:(short)sSex.intValue];
    
    nGroupInfo.bodyAge = [_dtFmt dateFromString:sBorn];
    
    nGroupInfo.fChest = [NSNumber numberWithFloat:sChest.floatValue];
    nGroupInfo.fWaist = [NSNumber numberWithFloat:sWaist.floatValue];
    
    nGroupInfo.bodyWgt = [NSNumber numberWithFloat:[sWgt floatValue]];
    nGroupInfo.wgtUnit = [NSNumber numberWithShort:(short)[sWun integerValue]];
    nGroupInfo.bodyHgt = [NSNumber numberWithFloat:[sHgt floatValue]];
    nGroupInfo.hgtUnit = [NSNumber numberWithShort:(short)[sHun integerValue]];
    //nGroupInfo.isAthlete = [NSNumber numberWithBool:([sAthlet isEqualToString:@"1"]? YES: NO)];
    nGroupInfo.athleteLvl = [NSNumber numberWithShort:[sAth intValue]];
    
    [_dtFmt setDateFormat:sInitDtFmt];
    
    NSError *error = nil;
    if (![managedObjectContext save:&error]) {
      return NO;
    }
    else {
      [self refreshCoreDataItems:nGroupInfo];
      //[_managedObjectContext refreshAllObjects];
      return YES;
    }
  }
  else {
    return NO;
  }
  
}

- (BOOL) updateMembBodyInfo:(NSInteger)nBodyId tagId:(NSString*)sTagId email:(NSString*)sEmail rmv:(BOOL)bRmv;

{
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_GroupInfo" inManagedObjectContext:managedObjectContext];
  [request setEntity:entity];
  request.fetchLimit = 1;
  
  NSPredicate *predicate =  [NSPredicate predicateWithFormat:@"bodyId=%ld", (long)nBodyId];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  [request setSortDescriptors:nil];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  _request.fetchLimit = 0;
  
  if(sTagId != nil) {
    if(mutableFetchResults != nil && mutableFetchResults.count > 0) {
      N_GroupInfo* nGroupInfo = [mutableFetchResults objectAtIndex:0];
      nGroupInfo.cardNo = sTagId;
      NSError *error = nil;
      if (![managedObjectContext save:&error]) {
        return NO;
      }
      else {
        [self refreshCoreDataItems:nGroupInfo];
        //[_managedObjectContext refreshAllObjects];
        return YES;
      }
    }
    else {
      return NO;
    }
  }
  else if(sEmail != nil) {
    if(mutableFetchResults != nil && mutableFetchResults.count > 0) {
      N_GroupInfo* nGroupInfo = [mutableFetchResults objectAtIndex:0];
      nGroupInfo.bodyEmail = sEmail;
      if(bRmv)
        nGroupInfo.groupId = [NSNumber numberWithInt:-1];
      NSError *error = nil;
      if (![managedObjectContext save:&error]) {
        return NO;
      }
      else {
        [self refreshCoreDataItems:nGroupInfo];
        //[_managedObjectContext refreshAllObjects];
        return YES;
      }
    }
    else {
      return NO;
    }
  }
  else
    return NO;
}

- (BOOL) updHrateStartEndTime:(H_Rate*)hRate startTime:(NSDate*)dtStart endTime:(NSDate*)dtEnd toSvr:(BOOL)bToSvr {
  BOOL bNetOk = [self isNetWorkConnAvailable];
  if(dtStart != nil) {
    hRate.hEnterDate = dtStart;
    _dtHrtStart = dtStart;
  }
  if(dtEnd != nil)
    hRate.hEndDate = dtEnd;
  
  if(bToSvr) {
    if(hRate.nLastUpdIdx.integerValue == -1)
      hRate.nLastUpdIdx =  [NSNumber numberWithInteger:(bNetOk?-1: 0)];
  }
  else {
    hRate.nLastUpdIdx =  [NSNumber numberWithInteger:0];
  }
  
  
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
      return NO;
  }
  else {
    [self refreshCoreDataItems:hRate];
  }

  //sent to server
  if(bToSvr && bNetOk) {
    NSInteger nHrateId = hRate.hRateId.integerValue;
    [self sendHrateDataToSvr:nHrateId bodyId:_bodyInfo.m_nBodyId measId:0 itemId:0 rateIdx:0 rngTxt:@"" measVal:0
                       cal:0.0 dur:0.0 dateTxt:@"" montxt:@"" time:dtEnd type:3];
    _dtHrtStart = nil;
  }
  return YES;
}

- (BOOL) fixHrateStartEndTime:(NSString*)sRateId startTime:(NSDate*)dtStart endTime:(NSDate*)dtEnd
{
  NSMutableArray* maHrate =  [self loadHrateInfo:sRateId.integerValue];
  if(maHrate != nil && maHrate.count > 0) {
    H_Rate* hRate = (H_Rate*)[maHrate objectAtIndex:0];
    if(hRate != nil) {
      BOOL bOK = [self updHrateStartEndTime: hRate startTime:dtStart endTime:dtEnd toSvr:YES];
      return bOK;
    }
    else {
      return NO;
    }
  }
  else {
    return NO;
  }
  
}
/*- (void) updHrateRcdMark
{
  NSMutableArray* pHrtData = [self loadHrateData:_nBodyId from:nil to:nil sort:YES last:NO syncOne:YES];
  NSUInteger nCount = pHrtData.count;
  for(NSUInteger i=0; i<nCount; i++) {
    H_Rate *pRate = [pHrtData objectAtIndex:i];
    pRate.hRateId = [NSNumber numberWithInteger:-pRate.hRateId.integerValue];
  }
  NSError *error = nil;
  if(nCount > 0)
    [_managedObjectContext save:&error];
  
  //rng
  pHrtData = [self loadHrateRngData:_nBodyId from:nil to:nil sort:YES last:NO sync:YES];
  nCount = pHrtData.count;
  for(NSUInteger i=0; i<nCount; i++) {
    H_RateRng *pRate = [pHrtData objectAtIndex:i];
    pRate.hRateId = [NSNumber numberWithInteger:-pRate.hRateId.integerValue];
    pRate.measId = [NSNumber numberWithInteger:-pRate.measId.integerValue];
  }
  if(nCount > 0)
      [_managedObjectContext save:&error];
  
  
  //item
  pHrtData = [self loadHrateItem:_nBodyId from:nil to:nil sort:YES avg:NO last:NO sync:YES];
  nCount = pHrtData.count;
  for(NSUInteger i=0; i<nCount; i++) {
    H_RateItem *pRate = [pHrtData objectAtIndex:i];
    pRate.hRateId = [NSNumber numberWithInteger:-pRate.hRateId.integerValue];
    pRate.hItemId = [NSNumber numberWithInteger:-pRate.hItemId.integerValue];
  }
  if(nCount > 0)
     [_managedObjectContext save:&error];
  
  //Ids reset
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  [userSetting setInteger:0 forKey:kNext_HrmMeasId];
  [userSetting setInteger:0 forKey:kNext_HrmItemId];
  
}*/

- (BOOL) updHrateSyncLastIdx:(NSString*)sHrateId lastIdx:(NSInteger)nIdx
{
  //return NO;
  //exception do that
  if(sHrateId == nil)
    return NO;
  
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_Rate" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = 1;
  
  NSPredicate *predicate =  [NSPredicate predicateWithFormat:@"hRateId=%@",sHrateId];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  [request setSortDescriptors:nil];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  _request.fetchLimit = 0;
  if(mutableFetchResults != nil && mutableFetchResults.count > 0) {
    H_Rate* pHrate = [mutableFetchResults objectAtIndex:0];
    pHrate.nLastUpdIdx = [NSNumber numberWithInteger:nIdx];
    
    NSError *error = nil;
    if (![managedObjectContext save:&error]) {
      return NO;
    }
    else {
      //NSSet *set = [managedObjectContext updatedObjects];
      [self refreshCoreDataItems:pHrate];
      //[managedObjectContext setStalenessInterval:0.0];
      return YES;
    }
  }
  else {
    return NO;
  }
}

- (BOOL) updHrateSyncState:(NSInteger)nIniId toId:(NSInteger)nNewId lastIdx:(NSInteger)nIdx
{
  NSBatchUpdateRequest *req = [[NSBatchUpdateRequest alloc] initWithEntityName:@"H_Rate"];
  if(nIniId == 0 && nNewId == 0)
    req.predicate = [NSPredicate predicateWithFormat:@"hRateId>%@", [NSNumber numberWithInteger:nIniId]];
  else
    req.predicate = [NSPredicate predicateWithFormat:@"hRateId=%@ AND ((nSyncType==2 OR nLastUpdIdx == -2) AND nLastUpdIdx != -1)", [NSNumber numberWithInteger:nIniId]];
  
  req.propertiesToUpdate = @{@"hRateId" : [NSNumber numberWithInteger:nNewId], @"nLastUpdIdx":[NSNumber numberWithInteger:nIdx]};
  //req.propertiesToUpdate = @{@"hRateId" : [NSNumber numberWithInteger:nNewId], @"nLastUpdIdx":[NSNumber numberWithInteger:nIdx], @"nSyncType":[NSNumber numberWithInt:2]};
  
  req.resultType = NSUpdatedObjectsCountResultType;
  NSBatchUpdateResult* res = (NSBatchUpdateResult *)[_managedObjectContext executeRequest:req error:nil];
  NSLog(@"%@ HrateData sync state updated", res.result);
  
  return res.accessibilityElementCount > 0;
  
}

- (BOOL) updateDldsHreteRecved:(NSInteger)nBodyId
{
  NSBatchUpdateRequest *req = [[NSBatchUpdateRequest alloc] initWithEntityName:@"H_Rate"];
  req.predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND nSyncType=1", nBodyId];
  req.propertiesToUpdate = @{@"nLastUpdIdx" : [NSNumber numberWithInteger:-1]};
  req.resultType = NSUpdatedObjectsCountResultType;
  NSBatchUpdateResult* res = (NSBatchUpdateResult *)[_managedObjectContext executeRequest:req error:nil];
  NSLog(@"%@ HrateData sync state updated", res.result);
  
  return res.accessibilityElementCount > 0;
}

- (BOOL) updateHrateToSvrStateforLastIdx:(NSInteger)nBodyId hRateId:(NSInteger) hRateId lastIdx:(NSInteger)nIdx
{
  NSBatchUpdateRequest *req = [[NSBatchUpdateRequest alloc] initWithEntityName:@"H_Rate"];
  req.predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND hRateId=%ld", nBodyId, hRateId];
  req.propertiesToUpdate = @{@"nLastUpdIdx" : [NSNumber numberWithInteger:nIdx]};
  req.resultType = NSUpdatedObjectsCountResultType;
  NSBatchUpdateResult* res = (NSBatchUpdateResult *)[_managedObjectContext executeRequest:req error:nil];
  NSLog(@"%@ HrateData sync state updated", res.result);
  //[self refreshCoreDataItems:req];
  
  return res.accessibilityElementCount > 0;
}

- (BOOL) updateHrateDataHrateId:(NSInteger)nIniId toId:(NSInteger)nNewId
{
  //return  NO;
  
  if(nIniId == 0 || nNewId == 0)
    return NO;
  
  /*NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_Rate" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = 1;
  
  NSPredicate *predicate =  [NSPredicate predicateWithFormat:@"hRateId=%@",sIniId];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  [request setSortDescriptors:nil];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  _request.fetchLimit = 0;
  if(mutableFetchResults != nil && mutableFetchResults.count > 0) {
    H_Rate* pHrate = [mutableFetchResults objectAtIndex:0];
    pHrate.hRateId = [NSNumber numberWithShort:sNewId.integerValue];
    pHrate.bodyId = pHrate.bodyId;
    pHrate.hEnterDate = pHrate.hEnterDate;
    pHrate.hEndDate = pHrate.hEndDate;
    pHrate.bMemory = pHrate.bMemory;
    pHrate.actType = pHrate.actType;
    pHrate.actComm = pHrate.actComm;
    
    [_managedObjectContext refreshObject:pHrate mergeChanges:YES];
    NSError *error = nil;
    if (![_managedObjectContext save:&error])
      return NO;
    else
      return YES;
  }
  else {
    return NO;
  }*/
  
  NSBatchUpdateRequest *req = [[NSBatchUpdateRequest alloc] initWithEntityName:@"H_Rate"];
  req.predicate = [NSPredicate predicateWithFormat:@"hRateId=%@", [NSNumber numberWithInteger:nIniId]];
  
  req.propertiesToUpdate = @{@"hRateId" : [NSNumber numberWithInteger:nNewId]};
  
  req.resultType = NSUpdatedObjectsCountResultType;
  NSBatchUpdateResult* res = (NSBatchUpdateResult *)[_managedObjectContext executeRequest:req error:nil];
  NSLog(@"%@ HrateData updated", res.result);
  
  //return res._columnsToUpdate > 0;
  //NSInteger n = res.accessibilityElementCount;
  return res.accessibilityElementCount > 0;
}

- (BOOL) updateHrateItemHrateIds:(NSInteger)nIniId toId:(NSInteger)nNewId;
{
  //return NO;
  
  if(nIniId == 0 || nNewId == 0)
    return NO;
  
  NSBatchUpdateRequest *req = [[NSBatchUpdateRequest alloc] initWithEntityName:@"H_RateRng"];
  req.predicate = [NSPredicate predicateWithFormat:@"hRateId=%@", [NSNumber numberWithInteger:nIniId]];
  req.propertiesToUpdate = @{@"hRateId" : [NSNumber numberWithInteger:nNewId]};
  req.resultType = NSUpdatedObjectsCountResultType;
  NSBatchUpdateResult *res = (NSBatchUpdateResult *)[_managedObjectContext executeRequest:req error:nil];
  NSLog(@"%@ HrateRng updated", res.result);
  
  req = [[NSBatchUpdateRequest alloc] initWithEntityName:@"H_RateItem"];
  req.predicate = [NSPredicate predicateWithFormat:@"hRateId=%@", [NSNumber numberWithInteger:nIniId]];
  req.propertiesToUpdate = @{@"hRateId" : [NSNumber numberWithInteger:nNewId]};
  req.resultType = NSUpdatedObjectsCountResultType;
  res = (NSBatchUpdateResult *)[_managedObjectContext executeRequest:req error:nil];
  NSLog(@"%@ HrateItem updated", res.result);
  
  //NSError *error = nil;
  //[_managedObjectContext save:&error];
  //[_managedObjectContext saveToPersistentStore:&error];
  //[self saveContext];
  
  //[_request dealloc];
  //request = nil;
  //_request = [[NSFetchRequest alloc] init];
  //[self initCoreData];
  
  
  return YES;
}

- (void) refreshCoreDataItems:(NSManagedObject *)object
{
  [_managedObjectContext refreshObject:object mergeChanges:YES];
}


- (BOOL) updateHrateDataActType:(NSString*)sHrateId actType:(short)nActType
{
  if(sHrateId == nil)
    return NO;
  
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_Rate" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = 1;
  
  NSPredicate *predicate =  [NSPredicate predicateWithFormat:@"hRateId=%@",sHrateId];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  [request setSortDescriptors:nil];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  _request.fetchLimit = 0;
  if(mutableFetchResults != nil && mutableFetchResults.count > 0) {
    H_Rate* pHrate = [mutableFetchResults objectAtIndex:0];
    pHrate.actType = [NSNumber numberWithShort:nActType];
    [self refreshCoreDataItems:pHrate];
    
    NSError *error = nil;
    if (![managedObjectContext save:&error])
      return NO;
    else
      return YES;
  }
  else {
    return NO;
  }
  
  /*if(sHrateId == nil || sTypeIdx == nil)
    return NO;
  
  NSBatchUpdateRequest *req = [[NSBatchUpdateRequest alloc] initWithEntityName:@"H_Rate"];
  req.predicate = [NSPredicate predicateWithFormat:@"hRateId=%@", [NSNumber numberWithInteger:sHrateId.integerValue]];
  req.propertiesToUpdate = @{@"actType" : [NSNumber numberWithInteger:sTypeIdx.intValue]};
  req.resultType = NSUpdatedObjectsCountResultType;
  NSBatchUpdateResult *res = (NSBatchUpdateResult *)[_managedObjectContext executeRequest:req error:nil];
  NSLog(@"%@ Hrate act type updated", res.result);
  
  return YES;*/
}

- (NSInteger) getNextBldId
{
  if(![self isNetWorkConnAvailable])
    return -1;
  /*NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_BdpData" inManagedObjectContext:managedObjectContext];
  [request setEntity:entity];
  [request setFetchLimit:1];
  
  NSPredicate *predicate = [NSPredicate predicateWithFormat:@"bodyId>%@", @"0"];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"measId" ascending:NO];
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *maRcdset = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  [request setFetchLimit:0];
  if (maRcdset == nil  || maRcdset.count == 0) {
    return 1;
  }
  N_BdpData* nRndRcd = (N_BdpData*)[maRcdset objectAtIndex:0];
  NSInteger nNextId = nRndRcd.measId.integerValue;
  return nNextId + 1;*/
  NSInteger nNextId = 0; 
  NSDictionary *measInfo = @{
                             @"BodyId" : [NSString stringWithFormat:@"%ld", (long)_bodyInfo.m_nBodyId],
                             @"hType" : @"21"
                             };
  
  NSString* sUrl = @"Host";
  NSMutableURLRequest *request = [self requestWebApiRouter:@"POST" url:sUrl data:measInfo];
  
  
  // 6.同步发送请求
  //[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
  NSData *data= [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
  if (data != nil) {
    NSString* sRecv = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
    sRecv = [sRecv substringWithRange: NSMakeRange(1, sRecv.length-2)];
    nNextId = (NSInteger)sRecv.integerValue;
  }
  return nNextId;
}

//bld pres insert
- (N_BdpData *) insertBdpData:(NSInteger)nBodyId bph:(short)nBph bpl:(short)nBpl hrt:(short)nPul date:(NSDate*)dtMeas toSvr:(BOOL)bToSvr
{
  //form next ID
  //NSMutableArray* fatArray = [self loadSqliteFatData:@"0" from:nil to:nil sort:false];
  NSInteger nId = [self getNextBldId]; 
    //if(fatArray == nil)
    //return nil;
    
    // NSInteger nId = fatArray.count + 1;
    
  N_BdpData *nBdpData = (N_BdpData *)[NSEntityDescription insertNewObjectForEntityForName:@"N_BdpData" inManagedObjectContext:_managedObjectContext];

    
  nBdpData.measId = [NSNumber numberWithInteger:nId];
  nBdpData.bodyId = [NSNumber numberWithInteger:nBodyId];
  nBdpData.bphVal = [NSNumber numberWithFloat:nBph];
  nBdpData.bplVal = [NSNumber numberWithFloat:nBpl];
  nBdpData.hRate = [NSNumber numberWithFloat:nPul];
  nBdpData.measDate = dtMeas;
  nBdpData.serialNo = @"Ble-BldPres";
    
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return NULL;
  }
  else {
    [self refreshCoreDataItems:nBdpData];
  }
  
  if(bToSvr && nId > 0)
    [self sendWfbsDataToSvr:nBodyId measId:nId sn:@"" wgt:0.0 wu:0 measTime:dtMeas
                      fat:0.0 wat:0.0 hgt:0.0 hu:0 oth:0
                      bph:nBph bpl:nBpl hrt:nPul
                      stp:0 dist:0.0 calory:0.0 type:2];
    return nBdpData;
}

- (BOOL) insertSyncBdpData:(NSNumber*)nMeasId date:(NSString*)sTime  hVal:(NSNumber*)nBlpHval lVal:(NSNumber*)nBlpLval bpm:(NSNumber*)nBlpBpm
{
  N_BdpData *nBdpData = (N_BdpData *)[NSEntityDescription insertNewObjectForEntityForName:@"N_BdpData" inManagedObjectContext:_managedObjectContext];
  
  NSString* sInitDtFmt = _dtFmt.dateFormat;
  [_dtFmt setDateFormat:@"MM/dd/yyyy HH:mm"];
  //NSDate* dtMeas =  [_dtFmt dateFromString:sTime];
  
  nBdpData.measId = nMeasId;
  nBdpData.bodyId = [NSNumber numberWithInteger:_bodyInfo.m_nBodyId];
  nBdpData.bphVal = nBlpHval;
  nBdpData.bplVal = nBlpLval;
  nBdpData.hRate = nBlpBpm;
  nBdpData.measDate = [_dtFmt dateFromString:sTime];
  nBdpData.serialNo = @"BleSync-BldPres";
  
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return NO;
  }
  else {
    [self refreshCoreDataItems:nBdpData];
  }
  
  [_dtFmt setDateFormat:sInitDtFmt];
  return YES;
}

- (NSInteger) getNextStpId
{
  if(![self isNetWorkConnAvailable])
    return -1;
  /*NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"P_Steps" inManagedObjectContext:managedObjectContext];
  [request setEntity:entity];
  [request setFetchLimit:1];
  
  NSPredicate *predicate = [NSPredicate predicateWithFormat:@"bodyId>%@", @"0"];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"measId" ascending:NO];
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *maRcdset = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  [request setFetchLimit:0];
  if (maRcdset == nil  || maRcdset.count == 0) {
    return 1;
  }
  N_BdpData* nRndRcd = (N_BdpData*)[maRcdset objectAtIndex:0];
  NSInteger nNextId = nRndRcd.measId.integerValue;
  return nNextId + 1;*/
  NSInteger nNextId = 0; 
  NSDictionary *measInfo = @{
                             @"BodyId" : [NSString stringWithFormat:@"%ld", (long)_bodyInfo.m_nBodyId],
                             @"hType" : @"31"
                             };
  
  NSString* sUrl = @"Host";
  NSMutableURLRequest *request = [self requestWebApiRouter:@"POST" url:sUrl data:measInfo];
  
  
  // 6.同步发送请求
  //[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
  NSData *data= [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
  if (data != nil) {
    NSString* sRecv = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
    sRecv = [sRecv substringWithRange: NSMakeRange(1, sRecv.length-2)];
    nNextId = (NSInteger)sRecv.integerValue;
  }
  return nNextId;
}


- (P_Steps *) insertStepsData:(NSInteger)nBodyId step:(int)nSteps dist:(float)fDist calory:(float)fCalories date:(NSDate*) dtMeas 
                          add:(BOOL)bAdd toSvr:(BOOL)bToSvr;
{
  NSInteger nId = [self getNextStpId];
  
    //check steps record start
  NSDate* dtFr = [dtMeas dateByAddingTimeInterval:-_OneDaySeconds];
  NSDate* dtTo = [dtMeas dateByAddingTimeInterval:_OneDaySeconds];
  NSMutableArray* maStep = [self loadStepsData:nBodyId from:dtFr to:dtTo sort:NO last:YES];
  BOOL bExitsDayRcd = maStep != nil && maStep.count > 0;

    //check steps record end
  P_Steps *pStepData = nil;
  if(bExitsDayRcd)
    pStepData = [maStep objectAtIndex:0];
  else
    pStepData = (P_Steps *)[NSEntityDescription insertNewObjectForEntityForName:@"P_Steps" inManagedObjectContext:_managedObjectContext];
    
  pStepData.measId = [NSNumber numberWithInteger:nId];
  pStepData.bodyId = [NSNumber numberWithInteger:nBodyId];
    
  if(bExitsDayRcd && bAdd) {
    int nStepsAdd = nSteps + pStepData.nSteps.intValue;
    float fDistAdd = fDist + pStepData.tDistances.floatValue;
    float fCalorAdd = fCalories + pStepData.tCalories.floatValue;
    pStepData.nSteps = [NSNumber numberWithInt:nStepsAdd];
    pStepData.tDistances = [NSNumber numberWithFloat:fDistAdd];
    pStepData.tCalories = [NSNumber numberWithFloat:fCalorAdd];
  }
  else {
    pStepData.nSteps = [NSNumber numberWithInt:nSteps];
    pStepData.tDistances = [NSNumber numberWithFloat:fDist];
    pStepData.tCalories = [NSNumber numberWithFloat:fCalories];
  }

  pStepData.measDate = dtMeas;
  pStepData.serialNo = @"Ble-PedoSn";
    
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return NULL;
  }
  else {
    [self refreshCoreDataItems:pStepData];
  }
  
  if(bToSvr && nId > 0)
    [self sendWfbsDataToSvr:nBodyId measId:nId sn:@"" wgt:0.0 wu:0 measTime:dtMeas
                        fat:0.0 wat:0.0 hgt:0.0 hu:0 oth:0
                        bph:0 bpl:0 hrt:0
                        stp:nSteps dist:fDist calory:fCalories type:3];
  
    return pStepData;
}

- (BOOL) insertSyncStepsData:(NSNumber*)nMeasId date:(NSString*)sTime  step:(NSNumber*)nSteps dist:(NSNumber*)nDist calory:(NSNumber*)nCalory
{
  P_Steps* pStepData = (P_Steps *)[NSEntityDescription insertNewObjectForEntityForName:@"P_Steps" inManagedObjectContext:_managedObjectContext];
  
  NSString* sInitDtFmt = _dtFmt.dateFormat;
  [_dtFmt setDateFormat:@"MM/dd/yyyy HH:mm:ss"];
  //NSDate* dtMeas = [_dtFmt dateFromString:sTime];
  
  pStepData.measId = nMeasId;
  pStepData.bodyId = [NSNumber numberWithInteger:_bodyInfo.m_nBodyId];
  
  pStepData.nSteps = nSteps;
  pStepData.tDistances = nDist;
  pStepData.tCalories = nCalory;
  
  pStepData.measDate = [_dtFmt dateFromString:sTime];
  pStepData.serialNo = @"StpSync-PedoSn";
  
  NSError *error = nil;
  if (![_managedObjectContext save:&error]) {
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
    //[alertView release];
    return NO;
  }
  else {
    [self refreshCoreDataItems:pStepData];
  }

  [_dtFmt setDateFormat:sInitDtFmt];
  return YES;
}


//load core wgt data
- (NSMutableArray*) loadWgtData:(NSInteger)nBodyId from:(NSDate*)sFr to:(NSDate*)sTo sort:(BOOL)bAsc last:(BOOL)bLast
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  //return nil;
  if(!_bIniCoreData)
    [self initCoreData];
  
    
    NSError *error = nil;
    NSManagedObjectContext* managedObjectContext = _managedObjectContext;
    //NSFetchRequest *request = [[NSFetchRequest alloc] init];
    NSFetchRequest *request = _request;
    request.fetchLimit = bLast? 1: 0;
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_WgtData" inManagedObjectContext:managedObjectContext];
    //NSPredicate *predicate;
    [request setEntity:entity];
    
    NSPredicate *predicate = nil;
    if(sFr != nil && sTo != nil) {
        predicate = [NSPredicate predicateWithFormat:@"nBodyId=%ld AND scaDateTime>%@ AND scaDateTime<=%@",(long)nBodyId, sFr, sTo];
        //predicate = [NSPredicate predicateWithFormat:@"nBodyId=%@ AND iOsDateTime>%@ AND iOsDateTime<=%@",sBodyId, sFr, sTo];
    }
    else {
        predicate = [NSPredicate predicateWithFormat:@"nBodyId=%ld", nBodyId];
    }
    [request setPredicate:predicate];
    
    // Order the events by creation date, most recent first.
    NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"iOsDateTime" ascending:bAsc];
    NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
    [request setSortDescriptors:sortDescriptors];
    
    //group by
    /*NSAttributeDescription* statusDesc = [entity.attributesByName objectForKey:@"nBodyId"];
     NSExpression *keyPathExpression = [NSExpression expressionForKeyPath: @"mWgtData"];
     NSExpression *valueExpression = [NSExpression expressionForFunction: @"average:"arguments:@[keyPathExpression]];
     
     NSExpressionDescription* exp = [[NSExpressionDescription alloc] init];
     [exp setName:@"AvgWgt"];
     [exp setExpression:valueExpression];
     [exp setExpressionResultType: NSInteger32AttributeType];
     //[exp setExpressionResultType:NSDecimalAttributeType];
     
     //[request setPropertiesToFetch:[NSArray arrayWithObjects:@"mWgtData", exp, nil]];
     //[request setPropertiesToFetch:[NSArray arrayWithObjects:statusDesc, exp, nil]];
     [request setPropertiesToFetch:@[exp]];
     
     [request setPropertiesToGroupBy:[NSArray arrayWithObject:@"nBodyId"]];
     [request setResultType:NSDictionaryResultType];*/
    //[request setPropertiesToFetch:@[exp, @"date"]];
    //NSFetchedResultsController *controller = [[NSFetchedResultsController alloc]
    //initWithFetchRequest:request managedObjectContext:managedObjectContext
    //sectionNameKeyPath:nil cacheName:@"<#Cache name#>"];
    //BOOL success = [controller performFetch:&error];
    //group by
    
    
    // Execute the fetch -- create a mutable copy of the result.
    NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
    if (mutableFetchResults == nil) {
        // Handle the error.
        NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
        UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
        [alertView show];
    }
    
    //int n = [mutableFetchResults count];
    //NSObject * obj = [mutableFetchResults objectAtIndex:0];
    
    // Set self's events array to the mutable array, then clean up.
    _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
    //[pCurView resetWgtMaxVal:m_nWgtArray];
    
    return _maCoreData;
}

- (NSMutableArray*) loadFatData:(NSInteger)nBodyId from:(NSDate*)sFr to:(NSDate*)sTo sort:(BOOL)bAsc last:(BOOL)bLast
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
    NSError *error = nil;
    NSManagedObjectContext* managedObjectContext = _managedObjectContext;
    //NSFetchRequest *request = [[NSFetchRequest alloc] init];
    NSFetchRequest *request = _request;
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_FatData" inManagedObjectContext:managedObjectContext];
    //NSPredicate *predicate;
    [request setEntity:entity];
    request.fetchLimit = bLast? 1: 0;
    
    NSPredicate *predicate = nil;
    if(sFr != nil && sTo != nil) {
        predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND measDate>%@ AND measDate<=%@ AND fatVal>0",nBodyId, sFr, sTo];
    }
    else {
        predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND fatVal>0", nBodyId];
    }
    [request setPredicate:predicate];
    
    // Order the events by creation date, most recent first.
    NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"measDate" ascending:bAsc];
    NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
    [request setSortDescriptors:sortDescriptors];
    
    
    // Execute the fetch -- create a mutable copy of the result.
    NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
    if (mutableFetchResults == nil) {
        // Handle the error.
        NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
        UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
        [alertView show];
    }
    
    // Set self's events array to the mutable array, then clean up.
    _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
    return _maCoreData;
}


- (NSMutableArray*) loadHrateInfo:(NSInteger)nHrateId
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //[managedObjectContext reset];
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_Rate" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = 1;
  
  NSPredicate *predicate = [NSPredicate predicateWithFormat:@"hRateId=%ld", nHrateId];
  if(predicate == nil)
    return nil;
  
  [request setPredicate:predicate];
  [request setSortDescriptors:nil];
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if (mutableFetchResults == nil) {
    // Handle the error.
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
  }
  
  // Set self's events array to the mutable array, then clean up.
  _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
  return _maCoreData;
}

- (NSMutableArray*) loadHrateData:(NSInteger)nBodyId from:(NSDate*)sFr to:(NSDate*)sTo sort:(BOOL)bAsc last:(BOOL)bLast syncDld:(BOOL)bDlds;
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  //NSFetchRequest *request = bSync?_request: [NSFetchRequest fetchRequestWithEntityName:@"H_Rate"];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_Rate" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = (bLast)? 1: 0;
    
  NSPredicate *predicate = nil;
  if(sFr != nil && sTo != nil) {
    predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND hEnterDate>%@ AND hEnterDate<=%@",nBodyId, sFr, sTo];
  }
  else if(nBodyId >= 0) {
    if(bDlds) {
      predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND nLastUpdIdx=-1", nBodyId];
    }
    else {
      predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld",nBodyId];
      //predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND hEndDate>hEnterDate",nBodyId];
    }
  }
  else {
    predicate = [NSPredicate predicateWithFormat:@"bodyId>%ld AND hEndDate>hEnterDate", nBodyId];
  }
  [request setPredicate:predicate];
    
  // Order the events by creation date, most recent first.
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"hEnterDate" ascending:bDlds?NO:bAsc];
  //NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:bSync?@"hRateId": @"hEnterDate" ascending:bAsc];
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
    
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if (mutableFetchResults == nil) {
    // Handle the error.
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
  }
    
  // Set self's events array to the mutable array, then clean up.
  _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
  return _maCoreData;

}

- (NSMutableArray*) loadHrateRngData:(NSInteger)nBodyId from:(NSDate*)sFr to:(NSDate*)sTo sort:(BOOL)bAsc last:(BOOL)bLast syncDld:(BOOL)bSync
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_RateRng" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = (bLast || bSync)? 1: 0;
  
  NSPredicate *predicate = nil;
  if(sFr != nil && sTo != nil) {
    predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND startTime>%@ AND startTime<=%@",nBodyId, sFr, sTo];
  }
  else if(nBodyId > 0) {
    if(bSync)
      predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND hRateId<0", nBodyId];
    else
      predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld", nBodyId];
  }
  else {
    predicate = [NSPredicate predicateWithFormat:@"bodyId>%d", 0];
  }
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  //NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"hRateId" ascending:bAsc];
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"startTime" ascending:bSync?NO:bAsc];
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if (mutableFetchResults == nil) {
    // Handle the error.
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
  }
  
  // Set self's events array to the mutable array, then clean up.
  _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
  return _maCoreData;
}

- (NSMutableArray*) loadHrateItem:(NSInteger)nBodyId from:(NSDate*)sFr to:(NSDate*)sTo sort:(BOOL)bAsc avg:(BOOL) bAvg last:(BOOL)bLast sync:(BOOL)bSync
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
    NSError *error = nil;
    NSManagedObjectContext* managedObjectContext = _managedObjectContext;
    //NSFetchRequest *request = [[NSFetchRequest alloc] init];
    NSFetchRequest *request = _request;
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_RateItem" inManagedObjectContext:managedObjectContext];
    //NSPredicate *predicate;
    [request setEntity:entity];
    request.fetchLimit = (bAvg || bLast)? 1: 0;
    
    NSPredicate *predicate = nil;
    if(sFr != nil && sTo != nil) {
        predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND hRateTime>%@ AND hRateTime<=%@", nBodyId, sFr, sTo];
    }
    else if(nBodyId > 0) {
      if(bSync)
        predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND hRateId<0", nBodyId];
      else
        predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld", nBodyId];
    }
    else {
        predicate = [NSPredicate predicateWithFormat:@"bodyId>%@", @"0"];
    }
    [request setPredicate:predicate];
    
    NSExpressionDescription *expressionDescription = nil;
    if(bAvg) {
        [request setSortDescriptors: nil];
        [request setPropertiesToFetch:nil];
        NSMutableArray *recdResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
        if(recdResults != nil && recdResults.count == 0)
            return nil;
        
        NSExpression* keyPathExpre = [NSExpression expressionForKeyPath:@"hRateValue"];
        NSExpression* avgExpress = [NSExpression expressionForFunction:@"average:" arguments:[NSArray arrayWithObject:keyPathExpre]];
        expressionDescription = [[NSExpressionDescription alloc] init];
        
        // The name is the key that will be used in the dictionary for the return value.
        [expressionDescription setName:@"hRate-Value"];//@"HrateAvgVal"];
        [expressionDescription setExpression:avgExpress];
        [expressionDescription setExpressionResultType:NSInteger16AttributeType];
        
        // Set the request's properties to fetch just the property represented by the expressions.
        //[request setPropertiesToFetch:[NSArray arrayWithObject:expressionDescription]];
        //request.returnsObjectsAsFaults = NSDictionaryResultType;
    }
    else/* if(bLast)*/ {
      NSSortDescriptor *sortDescriptor = nil;
      if(bLast)
        sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"hRateTime" ascending:NO];
      else
        sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"hRateTime" ascending:bAsc];
        NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
        [request setSortDescriptors:sortDescriptors];
    }
    
    
    // Execute the fetch -- create a mutable copy of the result.
    NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
    if (mutableFetchResults == nil) {
        // Handle the error.
        NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
        UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
        [alertView show];
    }
    
    // Set self's events array to the mutable array, then clean up.
    _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
    
    /*if(bLast && expressionDescription != nil)
        [expressionDescription release];
    [request release];*/
    [request setPropertiesToFetch:nil];
    
    return _maCoreData;
}

- (NSInteger) loadLastHrateId:(NSInteger)nBodyId sync:(BOOL)bSync
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  //NSFetchRequest *request = bSync?_request: [NSFetchRequest fetchRequestWithEntityName:@"H_Rate"];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_Rate" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = 1;
  
  NSPredicate* predicate = nil;
  if(bSync)
    predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND hRateId<0", nBodyId];
  else
    predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND hEndDate>hEnterDate", nBodyId];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"hEnterDate" ascending:NO];
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if (mutableFetchResults == nil) {
    // Handle the error.
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
  }
  
  // Set self's events array to the mutable array, then clean up.
  NSInteger nLastId = 0;
  _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
  if(_maCoreData.count > 0) {
    H_Rate* pHrate = [_maCoreData objectAtIndex:0];
    nLastId = pHrate.hRateId.integerValue;
  }
  
  request.fetchLimit = 0;
  return nLastId;
}

- (short) loadHrateItemAvg:(NSInteger)nBodyId hRateId:(NSInteger)nHrateId
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
  //return 80;
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_RateItem" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  //request.fetchLimit = 1;
  
  [request setSortDescriptors: nil];
  [request setPropertiesToFetch:nil];
  NSMutableArray *recdResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if(recdResults != nil && recdResults.count == 0)
    return 0;
  
  NSPredicate *predicate = nil;
  if(nHrateId != 0)
    predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND hRateId=%ld", nBodyId, nHrateId];
  else
    predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld", nBodyId];
  [request setPredicate:predicate];
  [request setResultType:NSDictionaryResultType];
  
  NSExpression* keyPathExpre = [NSExpression expressionForKeyPath:@"hRateValue"];
  NSExpression* avgExpress = [NSExpression expressionForFunction:@"average:" arguments:[NSArray arrayWithObject:keyPathExpre]];
  NSExpressionDescription* expressionDescription = [[NSExpressionDescription alloc] init];
  
  // The name is the key that will be used in the dictionary for the return value.
  [expressionDescription setName:@"hRate-Value"];//@"HrateAvgVal"];
  [expressionDescription setExpression:avgExpress];
  [expressionDescription setExpressionResultType:NSInteger16AttributeType];//NSDateAttributeType];
  [request setPropertiesToFetch:[NSArray arrayWithObject:expressionDescription]];
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if (mutableFetchResults == nil) {
    // Handle the error.
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
  }
  
  // Set self's events array to the mutable array, then clean up.
  short nAvgHrate = 0;
  //_maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
  if(mutableFetchResults.count > 0) {
    //H_RateItem* pItem = [_maCoreData objectAtIndex:0];
    //nAvgHrate = pItem.hRateValue.shortValue;
    
    NSDictionary *resultsDictionary = [mutableFetchResults lastObject];
    NSNumber* nAverage = [resultsDictionary valueForKey:@"hRate-Value"];
    nAvgHrate = nAverage.shortValue;
  }
  
  /*if(bLast && expressionDescription != nil)
   [expressionDescription release];
   [request release];*/
  
  [request setResultType:NSManagedObjectResultType];
  return nAvgHrate;
  
  //return 80;
  /*NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_RateItem" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = 1;
  
  [request setSortDescriptors: nil];
  [request setPropertiesToFetch:nil];
  NSMutableArray *recdResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if(recdResults != nil && recdResults.count == 0)
    return 0;
  
  NSPredicate *predicate = nil;
  if(nHrateId != 0)
    predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND hRateId=%ld", nBodyId, nHrateId];
  else
    predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld", nBodyId];
  [request setPredicate:predicate];
  [request setResultType:NSDictionaryResultType];
    
  NSExpression* keyPathExpre = [NSExpression expressionForKeyPath:@"hRateValue"];
  NSExpression* avgExpress = [NSExpression expressionForFunction:@"average:" arguments:[NSArray arrayWithObject:keyPathExpre]];
  NSExpressionDescription* expressionDescription = [[NSExpressionDescription alloc] init];
    
  // The name is the key that will be used in the dictionary for the return value.
  [expressionDescription setName:@"hRate-Value"];//@"HrateAvgVal"];
  [expressionDescription setExpression:avgExpress];
  //[expressionDescription setExpressionResultType:NSInteger16AttributeType];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if (mutableFetchResults == nil) {
    // Handle the error.
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
  }
  
  // Set self's events array to the mutable array, then clean up.
  short nAvgHrate = 0;
  _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
  if(_maCoreData.count > 0) {
    //NSDictionary *resultsDictionary = [mutableFetchResults lastObject];
    //NSNumber* nAverage = [resultsDictionary objectForKey:@"hRateValue"];
    //nAvgHrate = nAverage.shortValue;
    H_RateItem* pItem = [_maCoreData objectAtIndex:0];
    nAvgHrate = pItem.hRateValue.shortValue;
  }
  
  [request setPropertiesToFetch:nil];
  
  request.fetchLimit = 0;
  return nAvgHrate;*/
}

- (NSMutableArray*) loadHrateRngInfo:(NSInteger)nHrateId
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_RateRng" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = 0;
  
  NSPredicate *predicate = [NSPredicate predicateWithFormat:@"hRateId=%ld",nHrateId];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  //NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"hRateId" ascending:bAsc];
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"startTime" ascending:YES];
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if (mutableFetchResults == nil) {
    // Handle the error.
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
  }
  
  // Set self's events array to the mutable array, then clean up.
  _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
  return _maCoreData;
}

- (NSMutableArray*) loadHrateItemData:(NSInteger)nHrateId last:(BOOL)bLast
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_RateItem" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = bLast? 1: 0;
    
  NSPredicate *predicate =  [NSPredicate predicateWithFormat:@"hRateId=%ld", (long)nHrateId];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"hRateTime" ascending:YES];
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
    
    
    // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if (mutableFetchResults == nil) {
    // Handle the error.
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
  }
    
  // Set self's events array to the mutable array, then clean up.
  _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
  return _maCoreData;
    
}

- (NSMutableArray*) loadHrateItemLastData:(NSInteger)nHrateId dtLast:(NSDate*)dtLastDate
{
  
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_RateItem" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = 0;
  
  NSPredicate *predicate =  [NSPredicate predicateWithFormat:@"hRateId=%d AND hRateTime>%@",nHrateId, dtLastDate];
  //NSPredicate *predicate =  [NSPredicate predicateWithFormat:@"hRateId=%d",nHrateId];
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"hRateTime" ascending:YES];
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if (mutableFetchResults == nil) {
    // Handle the error.
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
  }
  
  // Set self's events array to the mutable array, then clean up.
  _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
  return _maCoreData;

}

- (NSMutableArray*) loadRateRngIdxData:(NSInteger)nBodyId from:(NSDate*)sFr to:(NSDate*)sTo sort:(BOOL)bAsc mon:(BOOL)bMon last:(BOOL)bLast
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
    NSError *error = nil;
    NSManagedObjectContext* managedObjectContext = _managedObjectContext;
    //NSFetchRequest *request = [[NSFetchRequest alloc] init];
    NSFetchRequest *request = _request;
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"H_RateRng" inManagedObjectContext:managedObjectContext];
    //NSPredicate *predicate;
    [request setEntity:entity];
    request.fetchLimit = bLast? 1: 0;
    
    NSPredicate *predicate = nil;
    if(sFr != nil && sTo != nil) {
        predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND measDate>%@ AND measDate<=%@",nBodyId, sFr, sTo];
    }
    else if(nBodyId > 0) {
        predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld", nBodyId];
    }
    else {
        predicate = [NSPredicate predicateWithFormat:@"bodyId>%d",  0];
    }
    [request setPredicate:predicate];
    
    // Order the events by creation date, most recent first.
    NSSortDescriptor *sortDate = [[NSSortDescriptor alloc] initWithKey:(bMon?@"sMonthTxt":@"sDateTxt") ascending:bAsc];
    //NSSortDescriptor *sortDate = [[NSSortDescriptor alloc] initWithKey:@"measDate" ascending:bAsc selector:@selector(localizedCaseInsensitiveCompare:)];
    /*NSSortDescriptor *sortDate = [[NSSortDescriptor alloc] initWithKey:@"measDate" ascending:bAsc comparator:^(id obja, id objb) {
     NSComparisonResult res = NSOrderedSame;
     if([obja isKindOfClass:[NSDate class]] && [objb isKindOfClass:[NSDate class]]) {
     NSString* sDate_a = [_dtBorn stringFromDate:obja];
     NSString* sDate_b = [_dtBorn stringFromDate:objb];
     res = [sDate_a compare:sDate_b];
     }
     return res;
     }];*/
    NSSortDescriptor *sortIdx = [[NSSortDescriptor alloc] initWithKey:@"rateIdx" ascending:bAsc];
    //NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortIdx, sortDate, nil];
    NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDate, sortIdx, nil];
    [request setSortDescriptors:sortDescriptors];
    
    
    // Execute the fetch -- create a mutable copy of the result.
    NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
    if (mutableFetchResults == nil) {
        // Handle the error.
        NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
        UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
        [alertView show];
    }
    
    // Set self's events array to the mutable array, then clean up.
    _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
    return _maCoreData;
    
}

- (NSMutableArray*) loadBdpData:(NSInteger)nBodyId from:(NSDate*)sFr to:(NSDate*)sTo sort:(BOOL)bAsc last:(BOOL)bLast
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
    NSError *error = nil;
    NSManagedObjectContext* managedObjectContext = _managedObjectContext;
    //NSFetchRequest *request = [[NSFetchRequest alloc] init];
    NSFetchRequest *request = _request;
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_BdpData" inManagedObjectContext:managedObjectContext];
    //NSPredicate *predicate;
    [request setEntity:entity];
    request.fetchLimit = bLast? 1: 0;
    
    NSPredicate *predicate = nil;
    if(sFr != nil && sTo != nil) {
        predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND measDate>%@ AND measDate<=%@", nBodyId, sFr, sTo];
    }
    else {
        predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld", nBodyId];
    }
    [request setPredicate:predicate];
    
    NSExpressionDescription* expressionDescription = nil;
    if(bLast && !bAsc) {
        [request setSortDescriptors: nil];
        [request setPropertiesToFetch:nil];
        NSMutableArray *recdResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
        if(recdResults != nil && recdResults.count == 0)
            return nil;
        
        NSExpression* keyPathExpre = [NSExpression expressionForKeyPath:@"bphVal"];
        NSExpression* avgExpress = [NSExpression expressionForFunction:@"min:" arguments:[NSArray arrayWithObject:keyPathExpre]];//"average"
        expressionDescription = [[NSExpressionDescription alloc] init];
        
        // The name is the key that will be used in the dictionary for the return value.
        [expressionDescription setName:@"dph_Val"];//@"HrateAvgVal"];
        [expressionDescription setExpression:avgExpress];
        [expressionDescription setExpressionResultType:NSInteger16AttributeType];
        
        // Set the request's properties to fetch just the property represented by the expressions.
        //[request setPropertiesToFetch:[NSArray arrayWithObject:expressionDescription]];
        //[request setSortDescriptors: nil];
    }
    else {
        if(bLast) {
            [request setSortDescriptors: nil];
            [request setPropertiesToFetch:nil];
            NSMutableArray *recdResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
            if(recdResults != nil && recdResults.count == 0)
                return nil;
        }
        // Order the events by creation date, most recent first.
        NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"measDate" ascending:bLast?NO:bAsc];
        NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
        [request setSortDescriptors:sortDescriptors];
    }
    
    
    // Execute the fetch -- create a mutable copy of the result.
    NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
    if (mutableFetchResults == nil) {
        // Handle the error.
        NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
        UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
        [alertView show];
    }
    
    // Set self's events array to the mutable array, then clean up.
    _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
    
    [request setPropertiesToFetch: nil];
    return _maCoreData;
}

- (NSMutableArray*) loadBdpAvgData:(NSInteger)nBodyId last:(NSUInteger)nCount
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
  NSError *error = nil;
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_BdpData" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = nCount;
  
  NSPredicate *predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld", nBodyId];
  [request setPredicate:predicate];
  
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"measDate" ascending:NO];
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];

  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if (mutableFetchResults == nil) {
    // Handle the error.
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
  }
  
  // Set self's events array to the mutable array, then clean up.
  _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
  
  request.fetchLimit = 0;
  [request setPropertiesToFetch: nil];
  
  return _maCoreData;
  
}

- (NSMutableArray*) loadStepsData:(NSInteger)nBodyId from:(NSDate*)sFr to:(NSDate*)sTo sort:(BOOL)bAsc last:(BOOL)bLast
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  
    NSError *error = nil;
    NSManagedObjectContext* managedObjectContext = _managedObjectContext;
    //NSFetchRequest *request = [[NSFetchRequest alloc] init];
    NSFetchRequest *request = _request;
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"P_Steps" inManagedObjectContext:managedObjectContext];
    //NSPredicate *predicate;
    [request setEntity:entity];
    request.fetchLimit = bLast? 1: 0;
    
    NSPredicate *predicate = nil;
    if(sFr != nil && sTo != nil) {
      predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld AND measDate>%@ AND measDate<=%@", nBodyId, sFr, sTo];
      //predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld", nBodyId];
    }
    else {
        if(bLast) {
            predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld", nBodyId];
        }
        else {
            predicate = [NSPredicate predicateWithFormat:@"bodyId=%ld", nBodyId];
        }
    }
    [request setPredicate:predicate];
    
    // Order the events by creation date, most recent first.
    NSSortDescriptor *sortDescriptor = nil;
    if(bLast) {
      if(!bAsc)
        sortDescriptor = [[NSSortDescriptor alloc] initWithKey:bAsc?@"tDistances": @"measDate" ascending:NO];
      else
        sortDescriptor = [[NSSortDescriptor alloc] initWithKey:bAsc?@"nSteps": @"nSteps" ascending:NO];
    }
    else {
        sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"measDate" ascending:bLast?NO:bAsc];
    }
    NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
    [request setSortDescriptors:sortDescriptors];
    
    // Execute the fetch -- create a mutable copy of the result.
    NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
    if (mutableFetchResults == nil) {
        // Handle the error.
        NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
        UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
        [alertView show];
    }
    
    // Set self's events array to the mutable array, then clean up.
    _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
    return _maCoreData;
}

//load core users/profile data
- (NSMutableArray*) loadMemberUserInfo:(NSInteger)nBodyId grpId:(NSInteger)nGroupId;
{
  if(_maCoreData != nil)
    [_maCoreData removeAllObjects];
  NSManagedObjectContext* managedObjectContext = _managedObjectContext;
  if((nBodyId <= 0 && nGroupId <= 0) || managedObjectContext == nil)
    return nil;
  
  NSError *error = nil;
  
  //NSFetchRequest *request = [[NSFetchRequest alloc] init];
  NSFetchRequest *request = _request;
  NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_GroupInfo" inManagedObjectContext:managedObjectContext];
  //NSPredicate *predicate;
  [request setEntity:entity];
  request.fetchLimit = 0;
  
  NSPredicate *predicate = nil;
  if(nBodyId > 0) {
    predicate = [NSPredicate predicateWithFormat:@"bodyId==%ld", nBodyId];
  }
  else if(nGroupId > 0) {
    predicate = [NSPredicate predicateWithFormat:@"groupId==%ld", (long)nGroupId];
  }
  else {
    predicate = [NSPredicate predicateWithFormat:@"groupId==%d", -1];
  }
  //if([bodyId integerValue] > 0 || [sGroupId integerValue] > 0)
  [request setPredicate:predicate];
  
  // Order the events by creation date, most recent first.
  NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"userIdx" ascending:YES]; //bodyEmail
  NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
  
  
  // Execute the fetch -- create a mutable copy of the result.
  NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
  if (mutableFetchResults == nil) {
    // Handle the error.
    NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
  }
  
  // Set self's events array to the mutable array, then clean up.
  _maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults];
  return _maCoreData;
  
}

- (N_GroupInfo*) loadMemberUserData:(NSInteger)nBodyId
{
  NSMutableArray* pUser = [self loadMemberUserInfo:nBodyId grpId:0];
  if(pUser != nil && pUser.count > 0) {
    N_GroupInfo* pBody = [pUser objectAtIndex:0];
    return pBody;
    
  }
  else {
    return nil;
  }
}

- (void) deleteRow:(NSString*)sTable key:(NSInteger)nKey
{
  NSManagedObjectContext *context = _managedObjectContext;
  NSEntityDescription *productEntity=[NSEntityDescription entityForName:sTable inManagedObjectContext:context];
  NSFetchRequest *fetch = _request;
  [fetch setEntity:productEntity];
  fetch.fetchLimit = 0;
  [fetch setSortDescriptors:nil];
  NSPredicate *p = [NSPredicate predicateWithFormat:@"hRateId==%ld", nKey];
  [fetch setPredicate:p];
  
  //... add sorts if you want them
  NSError *fetchError,  *error;
  NSArray *fetchedItems =[context executeFetchRequest:fetch error:&fetchError];
  if(fetchedItems == nil)
    return;
  for (NSManagedObject *rowItem in fetchedItems) {
    [context deleteObject:rowItem];
    [self refreshCoreDataItems:rowItem];
  }
  [context save:&error];
}


- (void) sendWfbsDataToSvr:(NSInteger)nBodyId  measId:(NSInteger)nMeasId sn:(NSString*)sSn wgt:(float)fWgt wu:(short)nWu measTime:(NSDate*) dtMeas
                       fat:(float)fFat wat:(float)fWat hgt:(float)fHgt hu:(short)hUn oth:(long long)nOth
                       bph:(short)nBph bpl:(short)nBpl hrt:(short)nPul
                       stp:(int)nSteps dist:(float)fDist calory:(float)fCalorie type:(short) nType
{
  if(![self isNetWorkConnAvailable])
    return;
  
  _bNetSessionEror = NO;
  
  NSString* sInitDtFmt = _dtFmt.dateFormat;
  [_dtFmt setDateFormat:@"MM/dd/yyyy HH:mm:ss"];
  NSString* sDtMeas = [_dtFmt stringFromDate:dtMeas];
  NSDictionary *measInfo = nil;
  if(nType == 0) { //wgt
    measInfo = @{
                 @"_nMeasWgtId": [NSString stringWithFormat:@"%ld", (long)nMeasId],
                 @"_sDevId" : sSn,
                 @"_nBodyId" : [NSString stringWithFormat:@"%ld", (long)nBodyId],
                 @"_fWgtVal" : [NSString stringWithFormat:@"%.3f", fWgt],
                 @"_nWgtUnit" : [NSString stringWithFormat:@"%i", nWu],
                 @"_sCurtDateTime" :sDtMeas,
                 /*@"ScaleNo" : sSn,*/
                 @"_nType" : [NSString stringWithFormat:@"%i", nType + 5]
                 };
  }
  else if(nType == 1) { //fat
    long nOth1 = nOth >> 32;
    long nOth2 = nOth & 0x0000ffff;
    measInfo = @{
                 @"_nMeasFatId": [NSString stringWithFormat:@"%ld", (long)nMeasId],
                 @"_sDevId" : @"BleScale",
                 @"_nBodyId" : [NSString stringWithFormat:@"%ld", (long)nBodyId],
                 @"_fFatVal" : [NSString stringWithFormat:@"%.3f", fFat],
                 @"_fWatVal" : [NSString stringWithFormat:@"%.3f", fWat],
                 @"_nOthVal1" : [NSString stringWithFormat:@"%ld", nOth1],
                 @"_nOthVal2" : [NSString stringWithFormat:@"%ld", nOth2],
                 @"_fBodyHgt" : [NSString stringWithFormat:@"%.3f", fHgt],
                 @"_nHgtUn" : [NSString stringWithFormat:@"%i", hUn],
                 @"_sCurtDateTime" :sDtMeas,
                 @"_nType" : [NSString stringWithFormat:@"%i", nType+5]
                 };
  }
  else if(nType == 2) { //bdp
    measInfo = @{
                 @"MeasId": [NSString stringWithFormat:@"%ld", (long)nMeasId],
                 @"BodyId" : [NSString stringWithFormat:@"%ld", (long)nBodyId],
                 @"BldpLval": [NSString stringWithFormat:@"%d", nBpl],
                 @"BldpHval" : [NSString stringWithFormat:@"%d", nBph],
                 @"Hrate" : [NSString stringWithFormat:@"%d", nPul],
                 @"MeasDate" : sDtMeas,
                 @"mType" : [NSString stringWithFormat:@"%i", nType]
                 };
  }
  else if(nType == 3 || nType == 255) { //step
    measInfo = @{
                 @"MeasId": [NSString stringWithFormat:@"%ld", (long)nMeasId],
                 @"BodyId" : [NSString stringWithFormat:@"%ld", (long)nBodyId],
                 @"Steps" : [NSString  stringWithFormat:@"%d", nSteps],
                 @"Dists" : [NSString stringWithFormat:@"%.3f", fDist],
                 @"StepCalory" : [NSString stringWithFormat:@"%.3f", fCalorie],
                 @"MeasDate" :sDtMeas,
                 @"mType" : [NSString stringWithFormat:@"%i", nType]
                 };
  }
  
  NSString* sUrl = nil;
  NSMutableURLRequest *request = nil;
  if(nType <= 1) {
    sUrl = [NSString stringWithFormat:@"Mfw"]; // old is Host
    request = [self requestWebApiRouter:@"POST" url:sUrl data:measInfo];
  }
  else {
    sUrl = [NSString stringWithFormat:@"Mwfb/%ld", (long)nBodyId];
    request = [self requestWebApiRouter:@"PUT" url:sUrl data:measInfo];
  }
  
  // 6.发送请求
  //NSURLConnection *conn = [[NSURLConnection alloc] initWithRequest:request delegate:self];
  [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
    if (data == nil || connectionError) {
      //AudioServicesPlaySystemSound(1112);
      return;
    }
  }];
  [_dtFmt setDateFormat:sInitDtFmt];
  
}

- (void) sendHrateDataToSvr:(NSInteger)nHrateId bodyId:(NSInteger)nBodyId measId:(NSInteger)nMeasId itemId:(NSInteger)nItemId
                    rateIdx:(short)nRateIdx rngTxt:(NSString*)sRngTxt measVal:(short)nHrateVal cal:(float)fCal dur:(float)fDur
                    dateTxt:(NSString*)sDateTxt montxt:(NSString*)sMonTxt time:(NSDate*)dtMeas type:(short) nType
{
  if(nHrateId <= 0 || dtMeas == nil)
    return;
  
  _bNetSessionEror = NO;
  /*if(!_bHostConn)
    [self ConnScaleHost:YES IpAddr:NULL];
  if(!_bHostConn)
    return;*/
  
  //[_ncitWiFiDev sendData:(char*)[sData UTF8String] Alert:NO];
  
  // 4.设置请求体（请求参数）
  // 创建一个描述订单信息的JSON数据
  NSString* sInitDtFmt = _dtFmt.dateFormat;
  [_dtFmt setDateFormat:@"MM/dd/yyyy HH:mm:ss.SSS"];
  NSString* sDtMeas = [_dtFmt stringFromDate:dtMeas];
  NSDictionary *measInfo = nil;
  if(nType == 0) {
    measInfo = @{
                 @"m_nHrateId": [NSString stringWithFormat:@"%ld", (long)nHrateId],
                 @"BodyId" : [NSString stringWithFormat:@"%ld", (long)nBodyId],
                 @"m_sStart" :sDtMeas,
                 @"hType" : [NSString stringWithFormat:@"%i", nType]
                 };
  }
  else if(nType == 1) {
    measInfo = @{
                 @"m_nMeasId": [NSString stringWithFormat:@"%ld", (long)nMeasId],
                 @"m_nHrateId": [NSString stringWithFormat:@"%ld", (long)nHrateId],
                 @"BodyId" : [NSString stringWithFormat:@"%ld", (long)nBodyId],
                 @"m_nRateIdx" : [NSString stringWithFormat:@"%d", nRateIdx],
                 @"m_sRateRng" : sRngTxt,
                 @"m_dCalBurned" : [NSString stringWithFormat:@"%.5f", fCal],
                 @"m_dDurMinute" :  [NSString stringWithFormat:@"%.4f", fDur],
                 @"m_dtRngStart" : sDtMeas,
                 @"m_sDateTxt" : sDateTxt,
                 @"m_sMonthTxt": sMonTxt,
                 @"hType" : [NSString stringWithFormat:@"%i", nType]
                 };
  }
  else if(nType == 2) {
    measInfo = @{
                 @"m_nItemId": [NSString stringWithFormat:@"%ld", (long)nItemId],
                 @"BodyId" : [NSString stringWithFormat:@"%ld", (long)nBodyId],
                 @"m_nHrateId": [NSString stringWithFormat:@"%ld", (long)nHrateId],
                 @"HrateVal" : [NSString stringWithFormat:@"%d", nHrateVal],
                 @"MeasTime" : sDtMeas,
                 @"hType" : [NSString stringWithFormat:@"%i", nType]
                 };
  }
  else if(nType == 3) {
    NSString* sStart = @"1900-1-1";
    if(_dtHrtStart != nil) {
      //[_dtFmt setDateFormat:@"yyyy-MM-dd HH:mm:ss.SSS"];
      sStart = [_dtFmt stringFromDate:_dtHrtStart];
    }
    measInfo = @{
                 @"m_nHrateId": [NSString stringWithFormat:@"%ld", (long)nHrateId],
                 @"BodyId" : [NSString stringWithFormat:@"%ld", (long)nBodyId],
                 @"m_sStart" : sStart,
                 @"m_sEnd" :sDtMeas,
                 @"hType" : [NSString stringWithFormat:@"%i", nType]
                 };
  }
  else if(nType == 9) {
    measInfo = @{
                 @"m_nHrateId": [NSString stringWithFormat:@"%ld", (long)nHrateId],
                 @"BodyId" : [NSString stringWithFormat:@"%ld", (long)nBodyId],
                 @"m_nMeasId": [NSString stringWithFormat:@"%ld", (long)nMeasId],
                 @"hType" : [NSString stringWithFormat:@"%i", nType]
                 };
  }
  [_dtFmt setDateFormat:sInitDtFmt];
  NSString* sUrl = [NSString stringWithFormat:@"Mhm/%ld", (long)nBodyId];
  NSMutableURLRequest *request = [self requestWebApiRouter:@"PUT" url:sUrl data:measInfo];
  
  
  // 6.发送请求
  //NSURLConnection *conn = [[NSURLConnection alloc] initWithRequest:request delegate:self];
  [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
    if (data == nil || connectionError) {
      //AudioServicesPlaySystemSound(1112);
      return;
    }
    
    NSString* sRecv = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
    sRecv = [sRecv substringWithRange: NSMakeRange(1, sRecv.length-2)];
    if(nType > 1 && ![sRecv isEqualToString:@"1"]) {
      //NSString* sTitle = [NSString stringWithFormat:@"Svr error: %@", sRecv];
      //[self showAlertBox:sTitle msg:@"Svr error happeneed"];
      if(_vcCurrent != nil && [_vcCurrent isKindOfClass:[HeaRateViewCtrl class]]) {
        [((HeaRateViewCtrl*)_vcCurrent) showMessage:@"Svr db operation exception"];
      }
    }
    else {
      if([_vcCurrent isKindOfClass:[HeaRateViewCtrl class]]) {
        [((HeaRateViewCtrl*)_vcCurrent) showMessage:@""];
      }
    }
    
  }];
  [_dtFmt setDateFormat:sInitDtFmt];
}

//delegate funcs
- (void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task didCompleteWithError:(NSError *)error
{
  //_lblMsg.text = error.description;
  if(error != nil) {
    //_lblMsg.text = @"APP Server Connection failed!";
    //_lblMsg.textColor = [UIColor redColor];
    //[self stopSyncProcess];
    _bNetSessionEror = YES;
    AudioServicesPlaySystemSound(1112);
  }
}

- (void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveData:(NSData *)data
{
  if (data == nil) {
    //[_actView stopAnimating];
    //_btnSyncData.hidden = NO;
    AudioServicesPlaySystemSound(1112);
    return;
  }
  
  //BOOL bShowProg = YES;
  /*if(_bSyncGetWgtReqst) {
    //_nSyncCurrentPack++;
    //[self storeSyncGetBlpData:data];
  }
  else {
    //[self stopSyncProcess];
  }*/
  //if(bShowProg)
  //[self performSelectorOnMainThread:@selector(showSyncProgress) withObject:nil waitUntilDone:NO];
}

/*- (NSMutableArray*) loadLastMeasData:(NSInteger)nBodyId
{
    //return nil;
    
    if(!_bIniCoreData)
        [self initCoreData];
    
    if(_maLastData != nil)
        [_maLastData removeAllObjects];
    else
        _maLastData = [[NSMutableArray alloc] initWithCapacity:16];
    
    NSError *error = nil;
    NSManagedObjectContext* managedObjectContext = _managedObjectContext;
    NSFetchRequest *request = _request;
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"N_WgtData" inManagedObjectContext:managedObjectContext];
    [request setEntity:entity];
    request.fetchLimit = 1;
    
    NSPredicate *predicate = predicate = [NSPredicate predicateWithFormat:@"nBodyId>=%ld", nBodyId];
    [request setPredicate:predicate];
    
    // Order the events by creation date, most recent first.
    NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"iOsDateTime" ascending:NO];
    NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
    [request setSortDescriptors:sortDescriptors];
    
    
    // Execute the fetch -- create a mutable copy of the result.
    NSMutableArray *mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
    if (mutableFetchResults == nil) {
        // Handle the error.
        NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
        UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
        [alertView show];
    }
    
    //_maCoreData = [NSMutableArray arrayWithArray:mutableFetchResults]
    
    NSManagedObject* pWgtRcd = nil;
    if(_maCoreData.count == 0) {
        NSManagedObject* pWgt = [[NSManagedObject alloc]init];
        pWgtRcd = [pWgt initWithEntity:entity insertIntoManagedObjectContext:managedObjectContext];
        //N_WgtData* pWgtRcd = [[[N_WgtData alloc] init] initWithEntity:entity insertIntoManagedObjectContext:managedObjectContext];
        ((N_WgtData*)pWgtRcd).mWgtData = [NSNumber numberWithFloat:0.0f];
        //[_maCoreData addObject:pWgtRcd];
    }
    else {
        pWgtRcd = [mutableFetchResults objectAtIndex:0];
    }
    [_maLastData addObject:pWgtRcd];
    
    //fat
    NSManagedObject* pFatRcd = nil;
    entity = [NSEntityDescription entityForName:@"N_FatData" inManagedObjectContext:managedObjectContext];
    predicate = [NSPredicate predicateWithFormat:@"nBodyId>=%ld", nBodyId];
    [request setPredicate:predicate];
    
    // Order the events by creation date, most recent first.
    sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"iOsDateTime" ascending:NO];
     sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
    [request setSortDescriptors:sortDescriptors];
    
    
    // Execute the fetch -- create a mutable copy of the result.
    mutableFetchResults = [[managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
    if (mutableFetchResults == nil) {
        // Handle the error.
        NSString *sErrMsg = [NSString stringWithFormat: @"Unresolved error %@, %@", error, [error userInfo]];
        UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Save error" message:sErrMsg delegate:self cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
        [alertView show];
    }
    if(mutableFetchResults.count == 0) {
        NSManagedObject* pFat = [[NSManagedObject alloc]init];
        pFatRcd = [pFat initWithEntity:entity insertIntoManagedObjectContext:managedObjectContext];
        ((N_FatData*)pFatRcd).fatVal = [NSNumber numberWithFloat:0.0f];
        [mutableFetchResults addObject:pFatRcd];
    }
    else {
        pFatRcd = [mutableFetchResults objectAtIndex:0];
    }
    [_maLastData addObject:pFatRcd];
    
    request.fetchLimit = 0;
    return _maLastData;
}*/

- (NSString*) getHourMinSec:(double)dSecds
{
    int nSecds = (int)(dSecds + 0.5);
    if(dSecds < 0)
      return @"0:00:00";
  
    short nHour = nSecds / 3600;
    int nLeft = nSecds - nHour * 3600;
    short nMin = nLeft / 60;
    short nScd = (short)(nLeft - nMin * 60 + 0.01);
    
    NSString* sInfo = [NSString stringWithFormat:@"%i:%02i:%02i",  nHour, nMin, nScd];
    return sInfo;
}


//delete
- (void) removeCoreData:(NSString*)sTable {
  
  /*NSFetchRequest *fetchRequest = [NSFetchRequest fetchRequestWithEntityName:sTable];
  fetchRequest.includesPropertyValues = NO;
  fetchRequest.includesSubentities = NO;
  
  NSError *error;
  NSArray *items = [_managedObjectContext executeFetchRequest:fetchRequest error:&error];
  
  for (NSManagedObject *managedObject in items) {
    [_managedObjectContext deleteObject:managedObject];
    NSLog(@"Deleted %@", sTable);
  }
  [_managedObjectContext save:&error];*/
  
  NSFetchRequest *request = _request;//[[NSFetchRequest alloc] init];
  NSEntityDescription *entity = [NSEntityDescription entityForName:sTable inManagedObjectContext:_managedObjectContext];
  if(entity == nil)
    return;
  
  [request setEntity:entity];
  request.fetchLimit = 0;
    
  NSPredicate *predicate = nil;
  //NSSortDescriptor *sortDescriptor = nil;
  if([sTable isEqualToString:@"N_WgtData"]) {
    predicate = [NSPredicate predicateWithFormat:@"nBodyId>0"];
    //sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"iOsDateTime" ascending:YES];
  }
  else {
    predicate = [NSPredicate predicateWithFormat:@"bodyId>0"];
    //sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"bodyId" ascending:YES];
  }
  [request setPredicate:predicate];
    
  NSArray *sortDescriptors = nil; //[[NSArray alloc] initWithObjects:sortDescriptor, nil];
  [request setSortDescriptors:sortDescriptors];
  
  NSError *error = nil;
  NSMutableArray *mutFetchResults = [[_managedObjectContext executeFetchRequest:request error:&error] mutableCopy];
    
  /*NSUInteger nCount = [mutFetchResults count];
  for(int nIdx=0; nIdx<nCount; nIdx++) {
    NSManagedObject *rcdToDelete = [mutFetchResults objectAtIndex:nIdx];
    [_managedObjectContext deleteObject:rcdToDelete];
  }*/
  for (NSManagedObject *managedObject in mutFetchResults) {
    [_managedObjectContext deleteObject:managedObject];
    [self refreshCoreDataItems:managedObject];
  }
  //[mutFetchResults removeAllObjects];
  
  //if(nCount > 0) {
    NSError *saveError = nil;
    if([_managedObjectContext save:&saveError] == NO) {
      NSAssert(NO, @"Remove data failed\n%@", [saveError localizedDescription]);
      abort();
    }
  //}
}

- (void) removeAllCoreData
{
    //_sBodyId = @"-1";
    //[_dirGrpMember removeAllObjects];
  [self removeCoreData:@"N_WgtData"];
  [self removeCoreData:@"N_FatData"];
  [self removeCoreData:@"N_BdpData"];
  [self removeCoreData:@"P_Steps"];
  
  [self removeCoreData:@"H_RateItem"];
  [self removeCoreData:@"H_Rate"];
  
  [self removeCoreData:@"N_GroupInfo"];
  [self removeCoreData:@"N_DataGoals"];
  
  [self removeCoreData:@"H_RateRng"];
    
  //[self formGroupMemberData];
}

- (void)deleteAllEntities:(NSString *)nameEntity
{
  NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] initWithEntityName:nameEntity];
  [fetchRequest setIncludesPropertyValues:NO]; //only fetch the managedObjectID
  
  NSError *error;
  NSArray *fetchedObjects = [_managedObjectContext executeFetchRequest:fetchRequest error:&error];
  for (NSManagedObject *object in fetchedObjects)
  {
    [_managedObjectContext deleteObject:object];
  }
  
  error = nil;
  [_managedObjectContext save:&error];
}

- (void) deleteCoreData {
  NSString* dbName = @"AccuroFit.sqlite";
  NSString *persistentStorePath = _dbPath;//[self.applicationDocumentsDirectory stringByAppendingPathComponent: _dbName];
    
   //force delete db file
   if ([[NSFileManager defaultManager] fileExistsAtPath:persistentStorePath]) {
      NSError *error = nil;
      BOOL oldStoreRemovalSuccess = [[NSFileManager defaultManager] removeItemAtPath:persistentStorePath error:&error];
      if(!oldStoreRemovalSuccess)
         NSAssert3(oldStoreRemovalSuccess, @"Unhandled error adding persistent store in %s at line %d: %@", __FUNCTION__, __LINE__, [error localizedDescription]);
   }
   persistentStorePath = [self.applicationDocumentsDirString stringByAppendingPathComponent: dbName];
   if ([[NSFileManager defaultManager] fileExistsAtPath:persistentStorePath]) {
     NSError *error = nil;
     BOOL oldStoreRemovalSuccess = [[NSFileManager defaultManager] removeItemAtPath:persistentStorePath error:&error];
     if(!oldStoreRemovalSuccess)
        NSAssert3(oldStoreRemovalSuccess, @"Unhandled error adding persistent store in %s at line %d: %@", __FUNCTION__, __LINE__, [error localizedDescription]);
   }
  
  //NSURL* newStoreURL = [[NSURL alloc] initWithString:_dbPath];
  //[[NSFileManager defaultManager] replaceItemAtURL:newStoreURL withItemAtURL:newStoreURL backupItemName:nil options:0 resultingItemURL:nil error:nil];
  
  _managedObjectContext = nil;
  _managedObjectModel = nil;
  _persistentStoreCoordinator = nil;
}

- (void)deleteDataHandler:(UIViewController *)viewCtrler tip:(bool)bTip {
  _nLastHrtId = -1;
  _nLastHrate = 0;
  _nCurtAvgHrt = 0;
  
  //_sCurUserEmail = @"";
  [self removeAllCoreData];
  [self deleteCoreData];
  
  [self initCoreData];
  [self.managedObjectContext reset];
  _bDeleteCoreData = YES;
  
  if(bTip) {
    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Delete Data"
                              message:@"All data are deleted!"
                              delegate:viewCtrler cancelButtonTitle:NSLocalizedString(@"OK", nil) otherButtonTitles:nil];
    [alertView show];
        //[alertView release];
  }
}

- (BOOL) dateIsToday:(NSDate*) dtMeas
{
    return YES;
    
    BOOL bOK = NO;
    BOOL bIos8 = [[[UIDevice currentDevice] systemVersion] floatValue] >= 8.0;
    if(bIos8)
        bOK = [[NSCalendar currentCalendar] isDateInToday:dtMeas];
    else
        bOK = YES;
    
    return bOK;
}

//exception
void uncaughtExceptionHandler(NSException *exception) {
  NSLog(@"CRASH: %@", exception);
  NSLog(@"Stack Trace: %@", [exception callStackSymbols]);
  // Internal error reporting
}

- (BOOL) updBodyRegHgt:(CGFloat)fHgtVal bFtUnit:(BOOL)bHgtFt
{
  if(_bodyInfo == nil)
    return NO;
  
  [self resetRegHgtUnit:bHgtFt?2:1];
  
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  _bodyInfo.fBodyHgt = fHgtVal;
  _bodyInfo.nHgtUn = bHgtFt?2:1;
  _bodyInfo.nHgtMm = fHgtVal * 1000 * (bHgtFt?_FtToMeter:1);
  
  [userSetting setFloat:_bodyInfo.fBodyHgt forKey:kReg_BodyHgt];
  [userSetting setFloat:_bodyInfo.nHgtUn forKey:kReg_HgtUnit];
  [userSetting setInteger:_bodyInfo.nHgtMm forKey:kReg_BodyHgtMm];
  
  NSInteger nGoalId = 0;
  NSString* sToSvrInfo = [NSString stringWithFormat:@"%f", _bodyInfo.fBodyHgt];
  NSString* sUnitType = [NSString stringWithFormat:@"%i", _bodyInfo.nHgtUn];
  NSString* sToSvrType = @"8";
  [self sendGoalDataToSvr:nGoalId body:_nLoginBodyId data:(NSString*)sToSvrInfo uType:sUnitType oType:sToSvrType];
  
  return YES;
}

- (BOOL) updTagIdDevTimeZone:(NSString*)sTagId devId:(NSString*)sDevId
{
  if(_bodyInfo == nil)
    return NO;
  
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  _bodyInfo.m_sTagId = sTagId;
  [userSetting setObject:_bodyInfo.m_sTagId forKey:kReg_TagId];
  
  [self sendTagDevInfoToSvr:_bodyInfo.m_nBodyId tagId:sTagId devId:sDevId];
  return YES;
}

- (BOOL) updBodyRegGender:(short)nSex
{
  if(_bodyInfo == nil)
    return NO;
  
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  _bodyInfo.nGender = nSex;
  
  [userSetting setInteger:_bodyInfo.nGender forKey:kReg_Gender];
  
  NSInteger nGoalId = 0;
  NSString* sToSvrInfo = [NSString stringWithFormat:@"%i", _bodyInfo.nGender];
  NSString* sUnitType = @"0";
  NSString* sToSvrType = @"6";
  
  [self sendGoalDataToSvr:nGoalId body:_nLoginBodyId data:(NSString*)sToSvrInfo uType:sUnitType oType:sToSvrType];
  
  [self setDefaultnMaxBpm];
  
  return YES;
}

- (BOOL) updBodyRegActLvl:(short)nActLvl
{
  if(_bodyInfo == nil)
    return NO;
  
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  _bodyInfo.nActLvl = nActLvl;
  
  [userSetting setInteger:_bodyInfo.nActLvl forKey:kReg_ActLevel];
  
  NSInteger nGoalId = 0;
  NSString* sToSvrInfo = [NSString stringWithFormat:@"%i", _bodyInfo.nActLvl];
  NSString* sUnitType = @"0";
  NSString* sToSvrType = @"9";
  
  [self sendGoalDataToSvr:nGoalId body:_nLoginBodyId data:(NSString*)sToSvrInfo uType:sUnitType oType:sToSvrType];
  
  return YES;
}

- (void) resetRegWgtInfo:(short)nNewUnit
{
  short nOldUnit = _bodyInfo.nWgtUn;
  if(nNewUnit != nOldUnit) {
    if(nNewUnit == 1)
      _bodyInfo.fGoalWgt *= _LbtoKg;
    else
      _bodyInfo.fGoalWgt /= _LbtoKg;
  }
  [self saveGoalData:_nLoginBodyId data:_bodyInfo.fGoalWgt dvUn:nNewUnit unitType:11 toSvr:NO];
}

- (void) resetRegHgtUnit:(short)nNewUnit
{
  short nOldUnit = _bodyInfo.nHgtUn;
  if(nNewUnit != nOldUnit) {
    if(nNewUnit == 1) {
      _bodyInfo.fChestSize *= _IntoCm;
      _bodyInfo.fWaistLine *= _IntoCm;
    }
    else {
      _bodyInfo.fChestSize /= _IntoCm;
      _bodyInfo.fWaistLine /= _IntoCm;
    }
  }
}

-(void) setDefaultnMaxBpm
{
  N_DataGoals* pGoal  = [self loadGoalData:_nLoginBodyId from:nil to:nil unitType:14 last:YES];
  if(pGoal == nil) {
    short nNoSetVal = [self calHrateFitnessRng:NO];
    if(_bodyInfo.nMaxBpm != nNoSetVal)
      _bodyInfo.nMaxBpm = nNoSetVal;
  }
  
}

- (BOOL) updBodyRegInfo:(short)nType info:(NSString*)sInfo unit:(short)nUnit
{
  if(_bodyInfo == nil)
    return NO;
  
  NSInteger nGoalId = -1;
  NSString* sToSvrInfo = sInfo;
  NSString* sUnitType = [NSString stringWithFormat:@"%i", nUnit];
  NSString* sToSvrType = [NSString stringWithFormat:@"%i", nType+1];
  
  NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  if(nType == 0) {
    nGoalId = 0;
    NSRange rng = [sInfo rangeOfString: @" "];
    rng = NSMakeRange(0, rng.location);
    NSString* sFirstName = [sInfo substringWithRange:rng];
    //NSInteger nLen = sFirstName.length;
    _bodyInfo.sFirst = sFirstName;
    [userSetting setObject:sFirstName forKey:kReg_FirstName];
  }
  else if(nType == 1) {
    nGoalId = 0;
    NSArray *listItems = [sInfo componentsSeparatedByString:@" "];
    if(listItems.count > 1) {
      //NSRange rng = [sInfo rangeOfString: @" "];
      //NSString* sLastName = [sInfo substringWithRange:rng];
      NSString* sLastName = listItems[1];
      _bodyInfo.sLast = sLastName;
      [userSetting setObject:sLastName forKey:kReg_LastName];
    }
  }
  else if(nType == 4) {
    nGoalId = 0;
    NSString* sInitDtFmt = _dtFmt.dateFormat;
    if([AppDelegate isLanguageChines])
      [_dtFmt setDateFormat:@"yyyy-MM-dd"];
    else
      [_dtFmt setDateFormat:@"MM/dd/yyyy"];
    _bodyInfo.dtBorn = [_dtFmt dateFromString:sInfo];
    [self setBodyYearAge:_bodyInfo.dtBorn];
    [userSetting setObject:sInfo forKey:kReg_BornDate];
    //[userSetting setInteger:_bodyInfo.nYearAge forKey:kReg_BodyAge];
    [_dtFmt setDateFormat:sInitDtFmt];
  }
  else if(nType == 6) {
    nGoalId = 0;
    _bodyInfo.fBodyWgt = sInfo.floatValue;
    [self resetRegWgtInfo: nUnit];
    _bodyInfo.nWgtUn = nUnit;
    //sUnitType = [NSString stringWithFormat:@"%d", _bodyInfo.nWgtUn];
    
    [userSetting setFloat:_bodyInfo.fBodyWgt forKey:kReg_BodyWgt];
    [userSetting setInteger:_bodyInfo.nWgtUn forKey:kReg_WgtUnit];
  }
  //else if(nType == 7) {
    //nGoalId = 0; see updBodyRegHgt
  //}
  /*else if(nType == 8) {
    NSInteger nActLevel = 1;
  }*/
  else if(nType == 9) {
    _bodyInfo.fGoalWgt = sInfo.floatValue;
    [self saveGoalData:_nLoginBodyId data:_bodyInfo.fGoalWgt dvUn:nUnit unitType:11 toSvr:YES];
    //[_viewController updateGoalData];
    _viewController.m_bUpdedWgtInfo = NO;
    sUnitType = @"11";
    return YES;
  }
  else if(nType == 10) {
    _bodyInfo.nGoalStep = sInfo.intValue;
    [self saveGoalData:_nLoginBodyId data:_bodyInfo.nGoalStep dvUn:nUnit unitType:12 toSvr:YES];
     sUnitType = @"12";
    return YES;
  }
  else if(nType == 11) {
    //nUnit = [AppDelegate isLanguageChines]?1:2;
    nUnit = _bodyInfo.nHgtUn;
    _bodyInfo.fGoalDist = sInfo.floatValue;
    _bodyInfo.nDistUnit = nUnit;
    [self saveGoalData:_nLoginBodyId data:_bodyInfo.fGoalDist dvUn:nUnit unitType:13 toSvr:YES];
    sUnitType = @"13";
    return YES;
  }
  else if(nType == 12) {
    _bodyInfo.nMaxBpm = sInfo.intValue;
    //short nMaxBpm = _bodyInfo.nMaxBpm;
    [self saveGoalData:_nLoginBodyId data:_bodyInfo.nMaxBpm dvUn:nUnit unitType:14 toSvr:YES];
    sUnitType = @"14";
    return YES;
  }
  else if(nType == 13) {
    nGoalId = 0;
    _bodyInfo.fChestSize = sInfo.floatValue;
    sToSvrType = @"23";
  }
  else if(nType == 14) {
    nGoalId = 0;
    _bodyInfo.fWaistLine = sInfo.floatValue;
     sToSvrType = @"24";
  }
  /*else { //min bpm
    nGoalId = 0;
    _bodyInfo.nMinBpm = sInfo.intValue;
    [self saveGoalData:_nBodyId data:_bodyInfo.nMinBpm dvUn:nUnit unitTppe:15 toSvr:YES];
    sUnitType = @"15";
    return YES;
  }*/
  else if(nType == 15) {
    _bodyInfo.fCaloriesDay = sInfo.floatValue;
    nUnit = 0;
    [self saveGoalData:_nLoginBodyId data:_bodyInfo.fCaloriesDay dvUn:nUnit unitType:15 toSvr:YES];
    return YES;
  }
  else if(nType == 16) {
    nUnit = 0;
    _bodyInfo.nGymVisitWeek = sInfo.integerValue;
    [self saveGoalData:_nLoginBodyId data:_bodyInfo.nGymVisitWeek dvUn:nUnit unitType:16 toSvr:YES];
    return YES;
  }
  
  if(nGoalId <= 0) {
    [self sendGoalDataToSvr:nGoalId body:_nLoginBodyId data:(NSString*)sToSvrInfo uType:sUnitType oType:sToSvrType];
  }
  
  if(nType == 6) {
    [self setDefaultnMaxBpm];
  }
  
  return YES;
}

- (BOOL) updMaxBpmVal:(NSString*)sInfo unit:(short)nUnit view:(UIViewController*)pView
{
  if(_bodyInfo == nil)
    return NO;
  
  //short nType = 12;
  //NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
  
    __block BOOL bRtn = YES;
    short nMaxHrt = [self calHrateFitnessRng:NO];
    if(nMaxHrt !=  sInfo.intValue) {
      UIAlertController* alert = [UIAlertController alertControllerWithTitle:@"Warnning!!" message:@"Change of Max Heart Rate will Affect You Intensity Point Total!"
                                                              preferredStyle:UIAlertControllerStyleAlert];
      
      UIAlertAction* deleteAction = [UIAlertAction actionWithTitle:@"Comfirm" style:UIAlertActionStyleDestructive
                                                           handler:^(UIAlertAction * action) {
                                                             _bodyInfo.nMaxBpm = sInfo.intValue;
                                                             [self saveGoalData:_nLoginBodyId data:_bodyInfo.nMaxBpm dvUn:nUnit unitType:14 toSvr:YES];
                                                             [(UIBodyProfileViewCtrl*)pView updateGoalData];
                                                           }];
      UIAlertAction* cancelAction = [UIAlertAction actionWithTitle:NSLocalizedString(@"Cancel", nil) style:UIAlertActionStyleCancel
                                                           handler:^(UIAlertAction * action) {
                                                             _bodyInfo.nMaxBpm = nMaxHrt;
                                                             [self saveGoalData:_nLoginBodyId data:_bodyInfo.nMaxBpm dvUn:nUnit unitType:14 toSvr:YES];
                                                             [(UIBodyProfileViewCtrl*)pView updateGoalData];
                                                             bRtn = NO;
                                                           }];
      
      [alert addAction:deleteAction];
      [alert addAction:cancelAction];
      
      if(_viewController != nil)
        [_viewController presentViewController:alert animated:YES completion:nil];
    }
    else {
      _bodyInfo.nMaxBpm = sInfo.intValue;
      [self saveGoalData:_nLoginBodyId data:_bodyInfo.nMaxBpm dvUn:nUnit unitType:14 toSvr:YES];
    }
    
    //sUnitType = @"14";
    return bRtn;
}

- (BOOL) updSvrIpAddress:(short)nSvrIdx
{
  if(nSvrIdx != _bodyInfo.nSvrIpIdx) {
    NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
    [userSetting setInteger:nSvrIdx forKey:kReg_BodySvrIdx];
    [self userLogout];
  }
  if(_bodyInfo != nil)
    _bodyInfo.nSvrIpIdx = nSvrIdx;
  return _bodyInfo != nil;
}

- (void) sendTagDevInfoToSvr:(NSInteger)nBodyId tagId:(NSString*) sTagId devId:(NSString*)sDevId
{
  _bNetSessionEror = NO;
  //hour diffenence
  NSTimeZone* timeZone = [NSTimeZone localTimeZone];
  int nHour = (int)-[timeZone secondsFromGMT] / 3600;
  NSString* sHour = [NSString stringWithFormat:@"-%i",nHour];
  NSString* sDlst = [NSString stringWithFormat:@"-%.0f", [timeZone daylightSavingTimeOffsetForDate:[NSDate date]]/3600];
  
  NSDictionary *measInfo = measInfo = @{
                                        @"m_nGoalId" : @"-1",
                                        @"BodyId" : [NSString stringWithFormat:@"%ld", (long)nBodyId],
                                        @"Email" :  _bodyInfo.sEmail,
                                        @"BodyTagId" : sTagId,
                                        @"RegDevId" : sDevId,
                                        @"_nHourOff" : sHour,
                                        @"_nHOurDst" : sDlst,
                                        @"_nType" : @"99"
                                        };
  
  NSString* sUrl = [NSString stringWithFormat:@"Mob/%ld", (long)nBodyId];
  NSMutableURLRequest *request = [self requestWebApiRouter:@"PUT" url:sUrl data:measInfo];
  
  
  // 6.发送请求
  //NSURLConnection *conn = [[NSURLConnection alloc] initWithRequest:request delegate:self];
  [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
    if (data == nil || connectionError) {
      //AudioServicesPlaySystemSound(1112);
      return;
    }
  }];
}

- (void) sendGoalDataToSvr:(NSInteger)nGoalId body:(NSInteger)nBodyId data:(NSString*)sDataVal uType:(NSString*)sUnitType oType:(NSString*) sOpType
{
  _bNetSessionEror = NO;
  NSDictionary *measInfo = measInfo = @{
                                        @"m_nGoalId" : [NSString stringWithFormat:@"%ld", (long)nGoalId],
                                        @"BodyId" : [NSString stringWithFormat:@"%ld", (long)nBodyId],
                                        @"RegDate" : sDataVal,
                                        @"m_fGoalVal" : sDataVal,
                                        @"m_nValUnit" : sUnitType,
                                        @"m_nUnitType" : sOpType,
                                        @"m_nTypeIdx" : sOpType
                                        };
 
  NSString* sUrl = [NSString stringWithFormat:@"Mob/%ld", (long)nBodyId];
  NSMutableURLRequest *request = [self requestWebApiRouter:@"PUT" url:sUrl data:measInfo];
  
  
  // 6.发送请求
  //NSURLConnection *conn = [[NSURLConnection alloc] initWithRequest:request delegate:self];
  [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
    if (data == nil || connectionError) {
      //AudioServicesPlaySystemSound(1112);
      return;
    }
  }];
}

//other assist fun

- (short) calHrateFitnessRng:(BOOL)bSetting
{
  short nAgeYear = _bodyInfo.nYearAge;
  float fBodyWgt = _bodyInfo.fBodyWgt;
  if(_bodyInfo.nWgtUn == 2)
    fBodyWgt *= _LbtoKg;
  
  short nMaxHrt = 0;
  if(bSetting)
    nMaxHrt = _bodyInfo.nMaxBpm;
  else
    nMaxHrt = (short)(206.3 - 0.71 * nAgeYear + 0.5);
    //nMaxHrt = (short)(210 - nAgeYear / 2 - fBodyWgt * 0.05 + 0.5);
  
    //if(_bodyInfo.nGender == 1)
    //nMaxHrt += 4;

  return nMaxHrt;
}

- (int) getHrateRngIdx:(short)nHrate maxLine:(float)yMaxLine count:(short)nBarCount
{
  int nIdx = 0;
  float yMinLine = yMaxLine * 0.5;
  
  float fDelta = (yMaxLine - yMinLine) / (nBarCount + 0);
  float fRng0 = yMinLine - 0.5;// - fDelta;
  float fRng1 = yMinLine + fDelta * 1;
  float fRng2 = yMinLine + fDelta * 2;
  float fRng3 = yMinLine + fDelta * 3;
  float fRng4 = yMinLine + fDelta * 4;
  
  if(nHrate < fRng0)
    nIdx = 1;
  else if(nHrate >= fRng0 && nHrate < fRng1)
    nIdx = 1;
  else if(nHrate >= fRng1 && nHrate < fRng2)
    nIdx = 2;
  else if(nHrate >= fRng2 && nHrate < fRng3)
    nIdx = 3;
  else if(nHrate >= fRng3 && nHrate <= fRng4)
    nIdx = 4;
  else if(nHrate > fRng4)
    nIdx = 5;
  
  
  return nIdx;
}

- (void) setUserBodyProfile:(NSArray*)jsonArray bodyInfo:(LoginBodyInfo*) bInfo
{
  for(NSDictionary *item in jsonArray) {
    NSString* sDataVal, *sDataUn, *sLocaInfo, *sProgNes,* sGrpNes;
    NSString* sUnitType = [item objectForKey:@"_nType"];
    NSString* sBorn = [item objectForKey:@"_sGoalDate"];
    int nUnitType = sUnitType.intValue;
    /*bInfo.fGoalWgt = 0.0f;
     bInfo.nGoalStep = 0;
     bInfo.fGoalDist = 0;
     
     bInfo.fCaloriesDay = 0.0f;
     bInfo.nGymVisitWeek = 0;*/
    
    if(nUnitType < 11) {
      //if(_nLoginBodyId == _bodyInfo.m_nBodyId) {
      NSString* sFirstNe = [item objectForKey:@"_sFirstNe"];
      NSString* sLastNe = [item objectForKey:@"_sLastNe"];
      _bodyInfo.sFirst = sFirstNe;
      _bodyInfo.sLast = sLastNe;
    
      NSString* sEmail = [item objectForKey:@"_sEmail"];
      if(sEmail != nil) {
        if([sEmail rangeOfString:@"@"].location != NSNotFound )
          _bodyInfo.sEmail = sEmail;
        else
          _bodyInfo.sEmail = @"";
      }
      
      
      NSString* sSex = [item objectForKey:@"_nGender"];
      NSString* sTagId = [item objectForKey:@"_sTagId"];
      NSString* sBodyWgt = [item objectForKey:@"_fStartWgt"];
      NSString* sWgtUn = [item objectForKey:@"_nWgtUn"];
      
      NSString* sBodyHgt =[item objectForKey:@"_fBodyHgt"];
      NSString* sHgtUn = [item objectForKey:@"_nHgtUn"];
      
      NSString* sChest = [item objectForKey:@"_fChestSize"];
      NSString* sWaist = [item objectForKey:@"_fWaistLine"];
      
      NSString* sActive = [item objectForKey:@"_nFitLvl"];
      
      if(sSex != nil)
        bInfo.nGender = (Byte)sSex.intValue;
      
      if(sTagId != nil/* && sTagId.length > 0*/)
        bInfo.m_sTagId = sTagId;
      
      if(sBodyWgt != nil/* && sBodyWgt.length > 0*/) {
        bInfo.fBodyWgt = sBodyWgt.floatValue;
        bInfo.nWgtUn = (Byte)sWgtUn.intValue;
      }
      
      //NSUInteger nLen = [sBodyHgt lengthOfBytesUsingEncoding:NSASCIIStringEncoding];
      if(sBodyHgt != nil/* && sBodyHgt.length > 0*/) {
        bInfo.fBodyHgt = sBodyHgt.floatValue;
        bInfo.nHgtUn = (Byte)sHgtUn.intValue;
        bInfo.nHgtMm = bInfo.fBodyHgt * 1000 * ((bInfo.nHgtUn==2)?_FtToMeter:1);
      }
      
      if(sActive != nil/* && sActive.length > 0*/)
        bInfo.nActLvl = sActive.intValue;
      
      if(sChest != nil/* && sChest.length > 0*/)
        bInfo.fChestSize = sChest.floatValue;
      if(sWaist != nil/* && sWaist.length > 0*/)
        bInfo.fWaistLine = sWaist.floatValue;
      
      if(sBorn != nil/* && sBorn.length > 0*/) {
        NSString* sDtFmt = _dtFmt.dateFormat;
        [_dtFmt setDateFormat:@"MM/dd/yyyy"];
        bInfo.dtBorn = [_dtFmt dateFromString:sBorn];
        [self setBodyYearAge:bInfo.dtBorn];
        [_dtFmt setDateFormat:sDtFmt];
      }
      
      NSString * sMgr = [item objectForKey:@"_bMgrBody"];
      NSString * sClubAdmin = [item objectForKey:@"_nClubAdmin"];
      
      bInfo.m_bMgr = sMgr.boolValue;
      bInfo.m_nClubAdmin = sClubAdmin.integerValue;
    }
    else {
      sDataVal = [item objectForKey:@"_fGoalVal"];
      sDataUn = [item objectForKey:@"_nGoalUn"];
      sLocaInfo = [item objectForKey:@"_sLocaInfo"];
      sProgNes = [item objectForKey:@"_sProgNes"];
      sGrpNes = [item objectForKey:@"_sGrpNes"];
    }
    
    if(nUnitType == 11) {
      //float fGoalWgt = sDataVal.floatValue;
      bInfo.fGoalWgt = sDataVal.floatValue;
    }
    else if(nUnitType == 12) {
      bInfo.nGoalStep = (int)sDataVal.integerValue;
    }
    else if(nUnitType == 13) {
      NSString* sDataUn = [item objectForKey:@"_nGoalUn"];
      bInfo.fGoalDist = sDataVal.floatValue;
      bInfo.nDistUnit = sDataUn.intValue;
    }
    else if(nUnitType == 14) {
      //bInfo.nMaxBpm = sDataVal.intValue;
      bInfo.nMaxBpm = sDataVal.intValue;
      NSUserDefaults *userSetting = [NSUserDefaults standardUserDefaults];
      [userSetting setInteger:sDataVal.intValue forKey:kReg_MaxBpm];
    }
    else if(nUnitType == 15)
      bInfo.fCaloriesDay = sDataVal.floatValue;
    else if(nUnitType == 16)
      bInfo.nGymVisitWeek = (short)sDataVal.intValue;
    
    if((NSNull *)sLocaInfo != [NSNull null] /*&& sLocaInfo.length >= 0*/)
      bInfo.sStoreLoc = sLocaInfo;
    else
      bInfo.sStoreLoc = nil;
    
    if((NSNull *)sProgNes != [NSNull null] /*&& sProgNes.length >= 0*/)
      bInfo.sProgram = sProgNes;
    else
      bInfo.sProgram = nil;
    
    if((NSNull *)sGrpNes!= [NSNull null] /*&& sGrpNes.length >= 0*/)
      bInfo.sTerms = sGrpNes;
    else
      bInfo.sTerms = nil;
  }
}

- (void) setLastBodyInfo
{
  self.m_nLastBodyId = _bodyInfo.m_nBodyId;
  self.m_sLastBodyName = [NSString stringWithFormat:@"%@ %@", _bodyInfo.sFirst, _bodyInfo.sLast];
}

- (void) getUserGoalData:(BOOL)bStore
{
  //store last member user name
  [self setLastBodyInfo];
  
  LoginBodyInfo* bInfo = self.m_bodyInfo;
  /*NSDictionary *measInfo = @{
                             @"BodyId" : [NSString stringWithFormat:@"%ld", (long)bInfo.m_nBodyId],
                             @"GoalWu" : @"255"
                             };*/
  
  NSString* sUrl = [NSString stringWithFormat:@"Host/%ld", (long)_nLoginBodyId];
  NSMutableURLRequest *request = [self requestWebApiRouter:@"DELETE" url:sUrl data:nil];
  
  
  // 6.同步发送请求
  [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
    //NSData *data= [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
    if (data != nil) {
      //NSString* sRecv = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
      
      NSError *e = nil;
      NSArray *jsonArray = [NSJSONSerialization JSONObjectWithData: data options: NSJSONReadingMutableContainers error: &e]; //
      // NSDictionary *jsonArray = [NSJSONSerialization JSONObjectWithData:data options:0 error:nil];
      if(jsonArray == nil)
        return;
      
      [self setUserBodyProfile: jsonArray bodyInfo:bInfo];
      
      
      if (_goalDelegate && [_goalDelegate respondsToSelector:@selector(updateGoalData)]) {
        [_goalDelegate updateGoalData];
        _viewController.m_bUpdedWgtInfo = NO;
      }
      /*if(bStore) {
        NSString* sTitle = [NSString stringWithFormat:@"Hello %@ %@", _bodyInfo.sFirst, _bodyInfo.sLast];
        [self.m_pRootViewCtrl setMsgTitle:sTitle];
      }*/
      
      if(bStore)
        [self storeRegInfoInUserDefaults];
    }
  }];
}

-(void) setPhoneCallNotication
{
  [[NSNotificationCenter defaultCenter] addObserver:self
   selector:@selector(statusBarFrameWillChange:)name:UIApplicationWillChangeStatusBarFrameNotification object:nil];
  
}

- (void)statusBarFrameWillChange:(NSNotification*)notification
{
  // respond to changes
  NSLog(@"STATUS BAR UPDATED");
  NSDictionary *statusBarDetail = [notification userInfo];
  NSValue *animationCurve = statusBarDetail[UIApplicationStatusBarFrameUserInfoKey];
  CGRect statusBarFrameBeginRect = [animationCurve CGRectValue];
  int statusBarHeight = (UIInterfaceOrientationIsPortrait([[UIApplication sharedApplication]statusBarOrientation])) ? statusBarFrameBeginRect.size.height : statusBarFrameBeginRect.size.width;
  
  NSLog(@"status bar height  %d", statusBarHeight);
}

-(void) viewDidDisappear:(BOOL)animated
{
  [[NSNotificationCenter defaultCenter] removeObserver:self name:UIApplicationBackgroundRefreshStatusDidChangeNotification object:nil];
}
/*- (int) getBodyGoalStep
{
  int nGoalSteps = _bodyInfo.nGoalStep;
  
  //test
  int n = _bodyInfo.m_nBodyId;
  NSString* sTagId = _bodyInfo.m_sTagId;
  float fSize = _bodyInfo.fChestSize;
  NSString* sLocaId = _bodyInfo.sStoreLoc;
  
  //test
  return nGoalSteps;
}*/

- (void) DeleteEnableDownload:(BOOL)bEnable
{
  /*(HeaRateViewCtrl* pPage = nil;//(HeaRateViewCtrl*)[_viewController lastObject];
  UIResponder *responder = _viewController;
  while (![responder isKindOfClass:[HeaRateViewCtrl class]]) {
    responder = [responder nextResponder];
    if (nil == responder) {
      pPage = (HeaRateViewCtrl*)responder;
    }
  }
  
  if(pPage != nil)
    [pPage EnableDownloadHrmMemory];*/
  self.m_bDownloadHrmMemory = bEnable;
}

- (void) showLogingInToolBar
{
 
  /*CGFloat fTitWid = 200;
  //UIImage* iNav = [UIImage imageNamed:@"ic-accuro-n.png"];
  UIImage* iNav = [self getImageScale:@"ic-accuro-n.png" scale:0.5];
  CGRect rt = _navController.navigationBar.frame;
  UIImageView *ivNav = [[UIImageView alloc] initWithFrame:CGRectMake((rt.size.width-fTitWid)/2 + 11, 10, fTitWid, 22)];
  [ivNav setImage:iNav];
  
  _navController.navigationBar.alpha = 0.5;
  ivNav.alpha = 1.0;
  
  rt.size.height -= 12;
  _navController.navigationBar.frame = rt;
  [_navController.navigationBar addSubview:ivNav];*/
}

- (void) showAlertBox:(NSString*) sTitle msg:(NSString*) sMsg;
{
  UIAlertController* alert = [UIAlertController alertControllerWithTitle:sTitle message:sMsg preferredStyle:UIAlertControllerStyleAlert];
  
  UIAlertAction* okAction = [UIAlertAction actionWithTitle:NSLocalizedString(@"OK", nil) style:UIAlertActionStyleDestructive
                                                       handler:^(UIAlertAction * action) {
                                                         
                                                       }];
  
  
  [alert addAction:okAction];
  
  //if(_viewController != nil)
  [self.m_pNavController presentViewController:alert animated:YES completion:nil];
}
@end
